From 86a6e6253d5b94fe021e52223fbfcf59ee6c5bdd Mon Sep 17 00:00:00 2001 From: David Cramer Date: Fri, 24 Apr 2020 13:20:08 +0200 Subject: [PATCH 01/20] remove old video config --- .../webpack.config.js | 1 - 1 file changed, 1 deletion(-) diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/webpack.config.js b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/webpack.config.js index 93b3c8dc9..2e0f62269 100755 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/webpack.config.js +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/webpack.config.js @@ -39,7 +39,6 @@ const cldCore = { ...sharedConfig, entry: { 'cloudinary': './js/src/main.js', - 'video': './css/src/video.scss', }, output: { path: path.resolve( process.cwd(), 'js' ), From a20b31eb44c0de04c5dbdc3d1280edff804c97c8 Mon Sep 17 00:00:00 2001 From: David Cramer Date: Fri, 24 Apr 2020 13:20:23 +0200 Subject: [PATCH 02/20] add styles and rebuild assets --- .../css/cloudinary.css | 2 +- .../css/src/components/_brand.scss | 82 +++++++++++-------- .../js/cloudinary.js | 2 +- 3 files changed, 50 insertions(+), 36 deletions(-) diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/css/cloudinary.css b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/css/cloudinary.css index 7df57b89b..de3d2c8a3 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/css/cloudinary.css +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/css/cloudinary.css @@ -1 +1 @@ -@font-face{font-family:cloudinary;src:url(../css/fonts/cloudinary.eot);src:url(../css/fonts/cloudinary.eot#iefix) format("embedded-opentype"),url(../css/fonts/cloudinary.ttf) format("truetype"),url(../css/fonts/cloudinary.woff) format("woff"),url(../css/cloudinary.svg#cloudinary) format("svg");font-weight:400;font-style:normal}.dashicons-cloudinary{speak:none;font-style:normal;font-weight:400;font-variant:normal;text-transform:none;line-height:1;-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale}.dashicons-cloudinary:before{font-family:cloudinary!important;content:"\e900"}.dashicons-cloudinary.success{color:#558b2f}.dashicons-cloudinary.error{color:#dd2c00}.dashicons-cloudinary.error:before{content:"\e901"}.dashicons-cloudinary.warning:before{content:"\e902"}.dashicons-cloudinary.warning{color:#fd9d2c}.column-cld_status{width:5.5em}.column-cld_status .dashicons-cloudinary{display:inline-block}.column-cld_status .dashicons-cloudinary:before{font-size:1.8rem}.form-field .error-notice,.form-table .error-notice{display:none;color:#dd2c00}.form-field input.cld-field:invalid,.form-table input.cld-field:invalid{border-color:#dd2c00}.form-field input.cld-field:invalid+.error-notice,.form-table input.cld-field:invalid+.error-notice{display:inline-block}.cloudinary-welcome{background-image:url(../css/logo.svg);background-repeat:no-repeat;background-size:153px;background-position:top 12px right 20px}.settings-image{max-width:100%;padding-top:5px}.settings-tabs>li{display:inline-block}.settings-tabs>li a{padding:.6em}.settings-tabs>li a.active{background-color:#fff}.settings-tab-section{padding:20px 0 0;max-width:1030px;position:relative}.settings-tab-section.cloudinary-welcome .settings-tab-section-fields-dashboard{display:flex;align-items:flex-start;align-content:flex-start;margin-top:40px}.settings-tab-section.cloudinary-welcome .settings-tab-section-fields-dashboard-description{width:55%;margin:0 auto 0 0}.settings-tab-section.cloudinary-welcome .settings-tab-section-fields-dashboard-content{width:35%;margin:0 auto}.settings-tab-section.cloudinary-welcome .settings-tab-section-fields-dashboard-content .dashicons{color:#9ea3a8}.settings-tab-section.cloudinary-welcome .settings-tab-section-card{margin-top:0}.settings-tab-section-fields .field-heading th{display:block;width:auto;color:#23282d;font-size:1.1em;margin:1em 0}.settings-tab-section-fields .field-heading td{display:none;visibility:hidden}.settings-tab-section-fields .regular-textarea{width:100%;height:60px}.settings-tab-section-fields .dashicons{text-decoration:none;vertical-align:middle}.settings-tab-section-fields a .dashicons{color:#5f5f5f}.settings-tab-section-fields-dashboard-error{font-size:1.2em;color:#5f5f5f}.settings-tab-section-fields-dashboard-error .dashicons{color:#ac0000}.settings-tab-section-fields-dashboard-error .button{font-size:1.1em;height:40px;line-height:40px;padding-right:40px;padding-left:40px}.settings-tab-section-fields-dashboard-success{font-size:1.2em;color:#23282d}.settings-tab-section-fields-dashboard-success.expanded{padding-top:40px}.settings-tab-section-fields-dashboard-success .dashicons{color:#4fb651}.settings-tab-section-fields-dashboard-success .button{font-size:1.1em;height:40px;line-height:40px;padding-right:40px;padding-left:40px}.settings-tab-section-fields-dashboard-success .description{color:#5f5f5f;font-weight:400;margin-top:12px}.settings-tab-section-card{box-sizing:border-box;border:1px solid #e5e5e5;background-color:#fff;box-shadow:0 1px 1px 0 rgba(0,0,0,.07);padding:20px 23px;margin-top:12px}.settings-tab-section-card .dashicons{font-size:1.4em}.settings-tab-section-card h2{font-size:1.8em;font-weight:400;margin-top:0}.settings-tab-section-card.pull-right{width:450px;padding:12px;float:right;position:relative;z-index:10}.settings-tab-section-card.pull-right img.settings-image{box-shadow:0 2px 4px 0 rgba(0,0,0,.5);border:1px solid #979797;margin-top:12px}.settings-tab-section-card.pull-right h3,.settings-tab-section-card.pull-right h4{margin-top:0}.settings-tab-section .field-row-cloudinary_url,.settings-tab-section .field-row-signup{display:block}.settings-tab-section .field-row-cloudinary_url td,.settings-tab-section .field-row-cloudinary_url th,.settings-tab-section .field-row-signup td,.settings-tab-section .field-row-signup th{display:block;width:auto;padding:10px 0 0}.settings-tab-section .field-row-cloudinary_url td .sign-up,.settings-tab-section .field-row-cloudinary_url th .sign-up,.settings-tab-section .field-row-signup td .sign-up,.settings-tab-section .field-row-signup th .sign-up{vertical-align:baseline}.settings-tab-section.connect .form-table{display:inline-block;width:auto;max-width:580px}.settings-valid{color:#558b2f;font-size:30px}.settings-valid-field{border-color:#558b2f!important}.settings-invalid-field{border-color:#dd2c00!important}.sync .spinner{display:inline-block;visibility:visible;float:none;margin:0 5px 0 0}.sync-media,.sync-media-progress{display:none}.sync-media-progress-outer{height:20px;margin:20px 0 10px;width:500px;background-color:#e5e5e5;position:relative}.sync-media-progress-outer .progress-bar{width:0;height:20px;background-color:#558b2f;transition:width .25s}.sync-media-progress-notice{color:#dd2c00}.sync-media-resource{width:100px;display:inline-block}.sync-media-error{color:#dd2c00}.sync-count{font-weight:700}.sync-details{margin-top:10px}.sync .button.start-sync,.sync .button.stop-sync{display:none;padding:0 16px}.sync .button.start-sync .dashicons,.sync .button.stop-sync .dashicons{line-height:2.2em}.sync .progress-text{padding:12px 4px 12px 12px;display:inline-block;font-weight:700}.sync .completed{max-width:300px;display:none}.cloudinary-widget{height:100%}.cloudinary-widget-wrapper{height:100%;overflow:hidden;background-image:url("data:image/svg+xml;base64,PHN2ZyBjbGFzcz0ic3Bpbm5lciIgdmlld0JveD0iLTQgLTQgMTUxIDEwMCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIj48c3R5bGU+QGtleWZyYW1lcyBjb2xvcnN7MCUsdG97c3Ryb2tlOiMwMDc4ZmZ9NTAle3N0cm9rZTojMGUyZjVhfX1Aa2V5ZnJhbWVzIGRhc2h7MCUsdG97c3Ryb2tlLWRhc2hvZmZzZXQ6NTYwfTUwJXtzdHJva2UtZGFzaG9mZnNldDowfX1ALXdlYmtpdC1rZXlmcmFtZXMgY29sb3JzezAlLHRve3N0cm9rZTojMDA3OGZmfTUwJXtzdHJva2U6IzBlMmY1YX19QC13ZWJraXQta2V5ZnJhbWVzIGRhc2h7MCUsdG97c3Ryb2tlLWRhc2hvZmZzZXQ6NTYwfTUwJXtzdHJva2UtZGFzaG9mZnNldDowfX08L3N0eWxlPjxwYXRoIGQ9Ik0xMjEuNjYzIDkwLjYzOGMtMS43OTYgMC05OS4zMy0uNDk4LTEwMS40NzQtMS40NzhDOC42ODUgODMuODc3IDEuMjUgNzIuMTk2IDEuMjUgNTkuMzk2YzAtMTYuNjU2IDEyLjc5Ny0zMC42MSAyOS4wNTItMzIuMzIzIDcuNDktMTUuNzA2IDIzLjE4Ni0yNS43MDcgNDAuNzE0LTI1LjcwNyAyMC45OCAwIDM5LjIxNSAxNC43NTIgNDMuOTQ1IDM0LjkwNyAxNS4wOS4yNDUgMjcuMjkgMTIuNjMgMjcuMjkgMjcuODIyIDAgMTEuOTY4LTcuNzM4IDIyLjU1LTE5LjI1NiAyNi4zMyIgc3Ryb2tlLXdpZHRoPSI5IiBzdHJva2UtbGluZWNhcD0icm91bmQiIGZpbGw9Im5vbmUiIGZpbGwtcnVsZT0iZXZlbm9kZCIgc3R5bGU9InRyYW5zZm9ybS1vcmlnaW46Y2VudGVyOy13ZWJraXQtYW5pbWF0aW9uOmRhc2ggMnMgZWFzZS1pbi1vdXQgaW5maW5pdGUsY29sb3JzIDhzIGVhc2UtaW4tb3V0IGluZmluaXRlO2FuaW1hdGlvbjpkYXNoIDJzIGVhc2UtaW4tb3V0IGluZmluaXRlLGNvbG9ycyA4cyBlYXNlLWluLW91dCBpbmZpbml0ZSIgc3Ryb2tlLWRhc2hhcnJheT0iMjgwIi8+PC9zdmc+");background-repeat:no-repeat;background-position:50%;background-size:150px}.attachment-actions .button.edit-attachment,.attachment-info .edit-attachment{display:none}.global-transformations-preview{position:relative;max-width:600px}.global-transformations-spinner{display:none}.global-transformations-button.button-primary{display:none;position:absolute;z-index:100}.global-transformations-url{margin-bottom:5px;margin-top:5px}.global-transformations-url-transformation{max-width:100px;overflow:hidden;text-overflow:ellipsis;color:#51a3ff}.global-transformations-url-file{color:#f2d864}.global-transformations-url-link{display:block;padding:16px;background-color:#262c35;text-decoration:none;color:#fff;border-radius:6px;overflow:hidden;text-overflow:ellipsis}.global-transformations-url-link:hover{color:#888;text-decoration:underline}.cld-tax-order-list-item{border:1px solid #efefef;padding:4px;margin:0 0 -1px;background-color:#fff}.cld-tax-order-list-item.no-items{color:#888;text-align:center;display:none}.cld-tax-order-list-item.no-items:last-child{display:block}.cld-tax-order-list-item.ui-sortable-helper{box-shadow:0 2px 5px rgba(0,0,0,.2)}.cld-tax-order-list-item-placeholder{background-color:#efefef;height:45px;margin:0}.cld-tax-order-list-item-handle{cursor:grab;margin-right:4px;color:#999}.cld-tax-order-list-type{width:45%;display:inline-block;margin-right:8px}.cld-tax-order-list-type input{margin-right:4px!important}.cloudinary-media-library{position:relative;margin-left:-20px}@media screen and (max-width:782px){.cloudinary-media-library{margin-left:-10px}} \ No newline at end of file +@font-face{font-family:cloudinary;src:url(../css/fonts/cloudinary.eot);src:url(../css/fonts/cloudinary.eot#iefix) format("embedded-opentype"),url(../css/fonts/cloudinary.ttf) format("truetype"),url(../css/fonts/cloudinary.woff) format("woff"),url(../css/cloudinary.svg#cloudinary) format("svg");font-weight:400;font-style:normal}.dashicons-cloudinary{speak:none;font-style:normal;font-weight:400;font-variant:normal;text-transform:none;line-height:1;-webkit-font-smoothing:antialiased;-moz-osx-font-smoothing:grayscale}.dashicons-cloudinary:before{font-family:cloudinary!important;content:"\e900"}.dashicons-cloudinary.success{color:#558b2f}.dashicons-cloudinary.error{color:#dd2c00}.dashicons-cloudinary.error:before{content:"\e901"}.dashicons-cloudinary.warning:before{content:"\e902"}.dashicons-cloudinary.warning{color:#fd9d2c}.column-cld_status{width:5.5em}.column-cld_status .dashicons-cloudinary{display:inline-block}.column-cld_status .dashicons-cloudinary:before{font-size:1.8rem}.form-field .error-notice,.form-table .error-notice{display:none;color:#dd2c00}.form-field input.cld-field:invalid,.form-table input.cld-field:invalid{border-color:#dd2c00}.form-field input.cld-field:invalid+.error-notice,.form-table input.cld-field:invalid+.error-notice{display:inline-block}.cloudinary-welcome{background-image:url(../css/logo.svg);background-repeat:no-repeat;background-size:153px;background-position:top 12px right 20px}.cloudinary-stats{display:inline-block;margin-left:25px}.cloudinary-stat{cursor:help}.cloudinary-percent{font-size:.8em;vertical-align:top;color:#0078ff}.settings-image{max-width:100%;padding-top:5px}.settings-tabs>li{display:inline-block}.settings-tabs>li a{padding:.6em}.settings-tabs>li a.active{background-color:#fff}.settings-tab-section{padding:20px 0 0;max-width:1030px;position:relative}.settings-tab-section.cloudinary-welcome .settings-tab-section-fields-dashboard{display:flex;align-items:flex-start;align-content:flex-start;margin-top:40px}.settings-tab-section.cloudinary-welcome .settings-tab-section-fields-dashboard-description{width:55%;margin:0 auto 0 0}.settings-tab-section.cloudinary-welcome .settings-tab-section-fields-dashboard-content{width:35%;margin:0 auto}.settings-tab-section.cloudinary-welcome .settings-tab-section-fields-dashboard-content .dashicons{color:#9ea3a8}.settings-tab-section.cloudinary-welcome .settings-tab-section-card{margin-top:0}.settings-tab-section-fields .field-heading th{display:block;width:auto;color:#23282d;font-size:1.1em;margin:1em 0}.settings-tab-section-fields .field-heading td{display:none;visibility:hidden}.settings-tab-section-fields .regular-textarea{width:100%;height:60px}.settings-tab-section-fields .dashicons{text-decoration:none;vertical-align:middle}.settings-tab-section-fields a .dashicons{color:#5f5f5f}.settings-tab-section-fields-dashboard-error{font-size:1.2em;color:#5f5f5f}.settings-tab-section-fields-dashboard-error .dashicons{color:#ac0000}.settings-tab-section-fields-dashboard-error .button{font-size:1.1em;height:40px;line-height:40px;padding-right:40px;padding-left:40px}.settings-tab-section-fields-dashboard-success{font-size:1.2em;color:#23282d}.settings-tab-section-fields-dashboard-success.expanded{padding-top:40px}.settings-tab-section-fields-dashboard-success .dashicons{color:#4fb651}.settings-tab-section-fields-dashboard-success .button{font-size:1.1em;height:40px;line-height:40px;padding-right:40px;padding-left:40px}.settings-tab-section-fields-dashboard-success .description{color:#5f5f5f;font-weight:400;margin-top:12px}.settings-tab-section-card{box-sizing:border-box;border:1px solid #e5e5e5;background-color:#fff;box-shadow:0 1px 1px 0 rgba(0,0,0,.07);padding:20px 23px;margin-top:12px}.settings-tab-section-card .dashicons{font-size:1.4em}.settings-tab-section-card h2{font-size:1.8em;font-weight:400;margin-top:0}.settings-tab-section-card.pull-right{width:450px;padding:12px;float:right;position:relative;z-index:10}.settings-tab-section-card.pull-right img.settings-image{box-shadow:0 2px 4px 0 rgba(0,0,0,.5);border:1px solid #979797;margin-top:12px}.settings-tab-section-card.pull-right h3,.settings-tab-section-card.pull-right h4{margin-top:0}.settings-tab-section .field-row-cloudinary_url,.settings-tab-section .field-row-signup{display:block}.settings-tab-section .field-row-cloudinary_url td,.settings-tab-section .field-row-cloudinary_url th,.settings-tab-section .field-row-signup td,.settings-tab-section .field-row-signup th{display:block;width:auto;padding:10px 0 0}.settings-tab-section .field-row-cloudinary_url td .sign-up,.settings-tab-section .field-row-cloudinary_url th .sign-up,.settings-tab-section .field-row-signup td .sign-up,.settings-tab-section .field-row-signup th .sign-up{vertical-align:baseline}.settings-tab-section.connect .form-table{display:inline-block;width:auto;max-width:580px}.settings-valid{color:#558b2f;font-size:30px}.settings-valid-field{border-color:#558b2f!important}.settings-invalid-field{border-color:#dd2c00!important}.sync .spinner{display:inline-block;visibility:visible;float:none;margin:0 5px 0 0}.sync-media,.sync-media-progress{display:none}.sync-media-progress-outer{height:20px;margin:20px 0 10px;width:500px;background-color:#e5e5e5;position:relative}.sync-media-progress-outer .progress-bar{width:0;height:20px;background-color:#558b2f;transition:width .25s}.sync-media-progress-notice{color:#dd2c00}.sync-media-resource{width:100px;display:inline-block}.sync-media-error{color:#dd2c00}.sync-count{font-weight:700}.sync-details{margin-top:10px}.sync .button.start-sync,.sync .button.stop-sync{display:none;padding:0 16px}.sync .button.start-sync .dashicons,.sync .button.stop-sync .dashicons{line-height:2.2em}.sync .progress-text{padding:12px 4px 12px 12px;display:inline-block;font-weight:700}.sync .completed{max-width:300px;display:none}.cloudinary-widget{height:100%}.cloudinary-widget-wrapper{height:100%;overflow:hidden;background-image:url("data:image/svg+xml;base64,PHN2ZyBjbGFzcz0ic3Bpbm5lciIgdmlld0JveD0iLTQgLTQgMTUxIDEwMCIgeG1sbnM9Imh0dHA6Ly93d3cudzMub3JnLzIwMDAvc3ZnIj48c3R5bGU+QGtleWZyYW1lcyBjb2xvcnN7MCUsdG97c3Ryb2tlOiMwMDc4ZmZ9NTAle3N0cm9rZTojMGUyZjVhfX1Aa2V5ZnJhbWVzIGRhc2h7MCUsdG97c3Ryb2tlLWRhc2hvZmZzZXQ6NTYwfTUwJXtzdHJva2UtZGFzaG9mZnNldDowfX1ALXdlYmtpdC1rZXlmcmFtZXMgY29sb3JzezAlLHRve3N0cm9rZTojMDA3OGZmfTUwJXtzdHJva2U6IzBlMmY1YX19QC13ZWJraXQta2V5ZnJhbWVzIGRhc2h7MCUsdG97c3Ryb2tlLWRhc2hvZmZzZXQ6NTYwfTUwJXtzdHJva2UtZGFzaG9mZnNldDowfX08L3N0eWxlPjxwYXRoIGQ9Ik0xMjEuNjYzIDkwLjYzOGMtMS43OTYgMC05OS4zMy0uNDk4LTEwMS40NzQtMS40NzhDOC42ODUgODMuODc3IDEuMjUgNzIuMTk2IDEuMjUgNTkuMzk2YzAtMTYuNjU2IDEyLjc5Ny0zMC42MSAyOS4wNTItMzIuMzIzIDcuNDktMTUuNzA2IDIzLjE4Ni0yNS43MDcgNDAuNzE0LTI1LjcwNyAyMC45OCAwIDM5LjIxNSAxNC43NTIgNDMuOTQ1IDM0LjkwNyAxNS4wOS4yNDUgMjcuMjkgMTIuNjMgMjcuMjkgMjcuODIyIDAgMTEuOTY4LTcuNzM4IDIyLjU1LTE5LjI1NiAyNi4zMyIgc3Ryb2tlLXdpZHRoPSI5IiBzdHJva2UtbGluZWNhcD0icm91bmQiIGZpbGw9Im5vbmUiIGZpbGwtcnVsZT0iZXZlbm9kZCIgc3R5bGU9InRyYW5zZm9ybS1vcmlnaW46Y2VudGVyOy13ZWJraXQtYW5pbWF0aW9uOmRhc2ggMnMgZWFzZS1pbi1vdXQgaW5maW5pdGUsY29sb3JzIDhzIGVhc2UtaW4tb3V0IGluZmluaXRlO2FuaW1hdGlvbjpkYXNoIDJzIGVhc2UtaW4tb3V0IGluZmluaXRlLGNvbG9ycyA4cyBlYXNlLWluLW91dCBpbmZpbml0ZSIgc3Ryb2tlLWRhc2hhcnJheT0iMjgwIi8+PC9zdmc+");background-repeat:no-repeat;background-position:50%;background-size:150px}.attachment-actions .button.edit-attachment,.attachment-info .edit-attachment{display:none}.global-transformations-preview{position:relative;max-width:600px}.global-transformations-spinner{display:none}.global-transformations-button.button-primary{display:none;position:absolute;z-index:100}.global-transformations-url{margin-bottom:5px;margin-top:5px}.global-transformations-url-transformation{max-width:100px;overflow:hidden;text-overflow:ellipsis;color:#51a3ff}.global-transformations-url-file{color:#f2d864}.global-transformations-url-link{display:block;padding:16px;background-color:#262c35;text-decoration:none;color:#fff;border-radius:6px;overflow:hidden;text-overflow:ellipsis}.global-transformations-url-link:hover{color:#888;text-decoration:underline}.cld-tax-order-list-item{border:1px solid #efefef;padding:4px;margin:0 0 -1px;background-color:#fff}.cld-tax-order-list-item.no-items{color:#888;text-align:center;display:none}.cld-tax-order-list-item.no-items:last-child{display:block}.cld-tax-order-list-item.ui-sortable-helper{box-shadow:0 2px 5px rgba(0,0,0,.2)}.cld-tax-order-list-item-placeholder{background-color:#efefef;height:45px;margin:0}.cld-tax-order-list-item-handle{cursor:grab;margin-right:4px;color:#999}.cld-tax-order-list-type{width:45%;display:inline-block;margin-right:8px}.cld-tax-order-list-type input{margin-right:4px!important}.cloudinary-media-library{position:relative;margin-left:-20px}@media screen and (max-width:782px){.cloudinary-media-library{margin-left:-10px}} \ No newline at end of file diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/css/src/components/_brand.scss b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/css/src/components/_brand.scss index 3e80e6340..34f384d33 100755 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/css/src/components/_brand.scss +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/css/src/components/_brand.scss @@ -1,72 +1,72 @@ @font-face { - font-family: 'cloudinary'; - src: url('fonts/cloudinary.eot?fj77m5'); - src: url('fonts/cloudinary.eot?fj77m5#iefix') format('embedded-opentype'), + font-family : 'cloudinary'; + src : url('fonts/cloudinary.eot?fj77m5'); + src : url('fonts/cloudinary.eot?fj77m5#iefix') format('embedded-opentype'), url('fonts/cloudinary.ttf?fj77m5') format('truetype'), url('fonts/cloudinary.woff?fj77m5') format('woff'), url('fonts/cloudinary.svg?fj77m5#cloudinary') format('svg'); - font-weight: normal; - font-style: normal; + font-weight : normal; + font-style : normal; } .dashicons { &-cloudinary { /* use !important to prevent issues with browser extensions that change fonts */ - speak: none; - font-style: normal; - font-weight: normal; - font-variant: normal; - text-transform: none; - line-height: 1; + speak : none; + font-style : normal; + font-weight : normal; + font-variant : normal; + text-transform : none; + line-height : 1; /* Better Font Rendering =========== */ - -webkit-font-smoothing: antialiased; - -moz-osx-font-smoothing: grayscale; + -webkit-font-smoothing : antialiased; + -moz-osx-font-smoothing : grayscale; &:before { - font-family: 'cloudinary' !important; - content: '\e900'; + font-family : 'cloudinary' !important; + content : '\e900'; } &.success { - color: $color-green; + color : $color-green; } &.error { - color: $color-red; + color : $color-red; &:before { - content: '\e901'; + content : '\e901'; } } &.warning { - color: $color-orange; + color : $color-orange; &:before { - content: '\e902'; + content : '\e902'; } } &.warning { - color: $color-orange; + color : $color-orange; } &.warning { - color: $color-orange; + color : $color-orange; } } } .column-cld_status { - width: 5.5em; + width : 5.5em; .dashicons { &-cloudinary { - display: inline-block; + display : inline-block; &:before { - font-size: 1.8rem; + font-size : 1.8rem; } } } @@ -74,22 +74,36 @@ .form-field, .form-table { .error-notice { - display: none; - color: $color-red; + display : none; + color : $color-red; } input.cld-field:invalid { - border-color: $color-red; + border-color : $color-red; + .error-notice { - display: inline-block; + display : inline-block; } } } -.cloudinary-welcome { - background-image: url("logo.svg"); - background-repeat: no-repeat; - background-size: 153px; - background-position: top 12px right 20px; +.cloudinary { + &-welcome { + background-image : url("logo.svg"); + background-repeat : no-repeat; + background-size : 153px; + background-position : top 12px right 20px; + } + &-stats{ + display: inline-block; + margin-left: 25px; + } + &-stat{ + cursor: help; + } + &-percent { + font-size : 0.8em; + vertical-align : top; + color : $color-blue; + } } diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/js/cloudinary.js b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/js/cloudinary.js index fd36fd6cc..9450213d7 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/js/cloudinary.js +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/js/cloudinary.js @@ -1 +1 @@ -!function(e){var t={};function i(n){if(t[n])return t[n].exports;var s=t[n]={i:n,l:!1,exports:{}};return e[n].call(s.exports,s,s.exports,i),s.l=!0,s.exports}i.m=e,i.c=t,i.d=function(e,t,n){i.o(e,t)||Object.defineProperty(e,t,{enumerable:!0,get:n})},i.r=function(e){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})},i.t=function(e,t){if(1&t&&(e=i(e)),8&t)return e;if(4&t&&"object"==typeof e&&e&&e.__esModule)return e;var n=Object.create(null);if(i.r(n),Object.defineProperty(n,"default",{enumerable:!0,value:e}),2&t&&"string"!=typeof e)for(var s in e)i.d(n,s,function(t){return e[t]}.bind(null,s));return n},i.n=function(e){var t=e&&e.__esModule?function(){return e.default}:function(){return e};return i.d(t,"a",t),t},i.o=function(e,t){return Object.prototype.hasOwnProperty.call(e,t)},i.p="",i(i.s=4)}([function(e,t){window,jQuery,jQuery(document).ready((function(e){e(document).on("tabs.init",(function(){var t=e(".settings-tab-trigger"),i=e(".settings-tab-section");e(this).on("click",".settings-tab-trigger",(function(n){var s=e(this),a=e(s.attr("href"));n.preventDefault(),t.removeClass("active"),i.removeClass("active"),s.addClass("active"),a.addClass("active"),e(document).trigger("settings.tabbed",s)})),e(".cld-field").not('[data-condition="false"]').each((function(){const t=e(this),i=t.data("condition");for(let n in i){const s=i[n],a=e("#field-"+n),r=t.closest("tr");a.on("change init",(function(){this.value===s||this.checked?r.show():r.hide()})),a.trigger("init")}})),e("#field-cloudinary_url").on("input change",(function(){let t=e(this),i=t.val();new RegExp(/^(?:CLOUDINARY_URL=)?(cloudinary:\/\/){1}(\d)*[:]{1}[^:@]*[@]{1}[^@]*$/g).test(i)?(t.addClass("settings-valid-field"),t.removeClass("settings-invalid-field")):(t.removeClass("settings-valid-field"),t.addClass("settings-invalid-field"))})).trigger("change")})),e(".render-trigger[data-event]").each((function(){var t=e(this),i=t.data("event");t.trigger(i,this)}))}))},function(e,t){if(wp.media&&window.CLDN){wp.media.events.on("editor:image-edit",(function(e){e.metadata.cldoverwrite=null,e.image.className.split(" ").indexOf("cld-overwrite")>=0&&(e.metadata.cldoverwrite="true")})),wp.media.events.on("editor:image-update",(function(e){let t=e.image.className.split(" ");e.metadata.cldoverwrite&&-1===t.indexOf("cld-overwrite")?t.push("cld-overwrite"):!e.metadata.cldoverwrite&&t.indexOf("cld-overwrite")>=0&&delete t[t.indexOf("cld-overwrite")],e.image.className=t.join(" ")}));let e=null,t=wp.media.string.props;wp.media.string.props=function(i,n){return i.cldoverwrite&&(i.classes=["cld-overwrite"],e=!0),t(i,n)},wp.media.post=function(t,i){if("send-attachment-to-editor"===t){let t=wp.media.editor.get().state().get("selection").get(i.attachment);t.attributes.transformations&&(i.attachment.transformations=t.attributes.transformations),(i.html.indexOf("cld-overwrite")>-1||!0===e)&&(i.attachment.cldoverwrite=!0,e=null)}return wp.ajax.post(t,i)};wp.media.controller.Library;let i=wp.media.view.MediaFrame.Select,n=wp.media.view.MediaFrame.Post,s=wp.media.view.MediaFrame.ImageDetails,a=wp.media.view.MediaFrame.VideoDetails,r=wp.media.View.extend({tagName:"div",className:"cloudinary-widget",template:wp.template("cloudinary-dam"),active:!1,toolbar:null,frame:null,ready:function(){let e=this.controller,t=this.model.get("selection"),i=this.model.get("library"),n=wp.media.model.Attachment;if(CLDN.mloptions.multiple=e.options.multiple,this.cid!==this.active){if(CLDN.mloptions.inline_container="#cloudinary-dam-"+e.cid,1===t.length){var s=n.get(t.models[0].id);void 0!==s.attributes.public_id&&(CLDN.mloptions.asset={resource_id:s.attributes.public_id})}else CLDN.mloptions.asset=null;window.ml=cloudinary.openMediaLibrary(CLDN.mloptions,{insertHandler:function(s){for(let a=0;a=100&&void 0!==e.started?(this.submitButton.style.display=this.hide,this.stopButton.style.display=this.show):e.pending>0?(this.submitButton.style.display=this.show,this.stopButton.style.display=this.hide):e.processing>0?this.stopButton.style.display=this.show:this.stopButton.style.display=this.hide,e.percent<100?(this.barSyncCount.innerText=e.total,this.progressCount.innerText=e.done,this.progress.style.display=this.show):(this.completed.style.display=this.show,this.progress.style.display=this.hide)},_start:function(e){e.preventDefault(),a.stopButton.style.display=a.show,a.submitButton.style.display=a.hide,a.pushAttachments()},_reset:function(e){a.submitButton.style.display=a.hide,a.getStatus()},_init:function(e){"undefined"!=typeof cloudinaryApi&&((document.attachEvent?"complete"===document.readyState:"loading"!==document.readyState)?e():document.addEventListener("DOMContentLoaded",e))}};var r=a;a._init((function(){a._reset(),a.submitButton.addEventListener("click",a._start),a.stopButton.addEventListener("click",a.stopSync)}));var o=i(1),l=i.n(o);const d={sample:{image:document.getElementById("transformation-sample-image"),video:document.getElementById("transformation-sample-video")},preview:{image:document.getElementById("sample-image"),video:document.getElementById("sample-video")},fields:document.getElementsByClassName("cld-field"),button:{image:document.getElementById("refresh-image-preview"),video:document.getElementById("refresh-video-preview")},spinner:{image:document.getElementById("image-loader"),video:document.getElementById("video-loader")},activeItem:null,elements:{image:[],video:[]},_placeItem:function(e){null!==e&&(e.style.display="block",e.style.visibility="visible",e.style.position="absolute",e.style.top=e.parentElement.clientHeight/2-e.clientHeight/2+"px",e.style.left=e.parentElement.clientWidth/2-e.clientWidth/2+"px")},_setLoading:function(e){this.button[e].style.display="block",this._placeItem(this.button[e]),this.preview[e].style.opacity="0.1"},_build:function(e){this.sample[e].innerHTML="",this.elements[e]=[];for(let t of this.fields){if(e!==t.dataset.context)continue;let i=t.value.trim();if(i.length){if("select-one"===t.type){if("none"===i)continue;i=t.dataset.meta+"_"+i}else{let e=t.dataset.context;i=this._transformations(i,e,!0)}i&&this.elements[e].push(i)}}let t="";this.elements[e].length&&(t="/"+this.elements[e].join(",").replace(/ /g,"%20")),this.sample[e].textContent=t,this.sample[e].parentElement.href="https://res.cloudinary.com/demo/"+this.sample[e].parentElement.innerText.trim().replace("../","").replace(/ /g,"%20")},_clearLoading:function(e){this.spinner[e].style.visibility="hidden",this.activeItem=null,this.preview[e].style.opacity=1},_refresh:function(e,t){e&&e.preventDefault();let i=this,n=CLD_GLOBAL_TRANSFORMATIONS[t].preview_url+i.elements[t].join(",")+CLD_GLOBAL_TRANSFORMATIONS[t].file;if(this.button[t].style.display="none",this._placeItem(this.spinner[t]),"image"===t){let e=new Image;e.onload=function(){i.preview[t].src=this.src,i._clearLoading(t),e.remove()},e.onerror=function(){alert(CLD_GLOBAL_TRANSFORMATIONS[t].error),i._clearLoading(t)},e.src=n}else{let e=i._transformations(i.elements[t].join(","),t);samplePlayer.source({publicId:"dog",transformation:e}),i._clearLoading(t)}},_transformations:function(e,t,i=!1){let n=CLD_GLOBAL_TRANSFORMATIONS[t].valid_types,s=null,a=e.split("/"),r=[];for(let e=0;e{const n=!!i.length&&jQuery('[data-item="'+s+":"+i[0].id+'"]');n.length?n.remove():(jQuery(`.cld-tax-order-list-item:contains(${r})`).remove(),--e.startId),this.processTags(t)})}),jQuery("body").on("change",".selectit input",(function(){const t=jQuery(this),i=t.val(),n=t.is(":checked"),s=t.parent().text().trim();!0===n?e.tags.find(`[data-item="category:${i}"]`).length||e._pushItem(`category:${i}`,s):e.tags.find(`[data-item="category:${i}"]`).remove()}))},_createItem:function(e,t){const i=jQuery("
  • "),n=jQuery(""),s=jQuery("");return i.addClass("cld-tax-order-list-item").attr("data-item",e),s.addClass("cld-tax-order-list-item-input").attr("type","hidden").attr("name","cld_tax_order[]").val(e),n.addClass("dashicons dashicons-menu cld-tax-order-list-item-handle"),i.append(n).append(t).append(s),i},_pushItem:function(e,t){let i=this._createItem(e,t);this.tags.append(i)},_sortable:function(){jQuery(".cld-tax-order-list").sortable({connectWith:".cld-tax-order",axis:"y",handle:".cld-tax-order-list-item-handle",placeholder:"cld-tax-order-list-item-placeholder",forcePlaceholderSize:!0,helper:"clone"})}};if(void 0!==window.CLDN&&(u._init(),jQuery("[data-wp-lists] .selectit input[checked]").map((e,t)=>{jQuery(t).trigger("change")})),wp.data&&wp.data.select("core/editor")){const e={};wp.data.subscribe((function(){let t=wp.data.select("core").getTaxonomies();if(t)for(let i in t){const n=wp.data.select("core/editor").getEditedPostAttribute(t[i].rest_base);e[t[i].slug]=n}}));const t=wp.element.createElement,i=i=>{class n extends i{constructor(e){super(e),this.currentItems=jQuery(".cld-tax-order-list-item").map((e,t)=>jQuery(t).data("item")).get()}makeItem(e){if(this.currentItems.includes(this.getId(e)))return;const t=this.makeElement(e);jQuery("#cld-tax-items").append(t)}removeItem(e){const t=jQuery(`[data-item="${this.getId(e)}"]`);t.length&&(t.remove(),this.currentItems=this.currentItems.filter(t=>t!==this.getId(e)))}findOrCreateTerm(e){return(e=super.findOrCreateTerm(e)).then(e=>this.makeItem(e)),e}onChange(t){super.onChange(t);const i=this.pickItem(t);i&&(e[this.props.slug].includes(i.id)?this.makeItem(i):this.removeItem(i))}pickItem(e){if("object"==typeof e){if(e.target){for(let t in this.state.availableTerms)if(this.state.availableTerms[t].id===parseInt(e.target.value))return this.state.availableTerms[t]}else if(Array.isArray(e)){let t=this.state.selectedTerms.filter(t=>!e.includes(t))[0];return void 0===t&&(t=e.filter(e=>!this.state.selectedTerms.includes(e))[0]),this.state.availableTerms.find(e=>e.name===t)}}else if("number"==typeof e){for(let t in this.state.availableTerms)if(this.state.availableTerms[t].id===e)return this.state.availableTerms[t]}else{let t;if(e.length>this.state.selectedTerms.length)for(let i in e)-1===this.state.selectedTerms.indexOf(e[i])&&(t=e[i]);else for(let i in this.state.selectedTerms)-1===e.indexOf(this.state.selectedTerms[i])&&(t=this.state.selectedTerms[i]);for(let e in this.state.availableTerms)if(this.state.availableTerms[e].name===t)return this.state.availableTerms[e]}}getId(e){return`${this.props.slug}:${e.id}`}makeElement(e){const t=jQuery("
  • "),i=jQuery(""),n=jQuery("");return t.addClass("cld-tax-order-list-item").attr("data-item",this.getId(e)),n.addClass("cld-tax-order-list-item-input").attr("type","hidden").attr("name","cld_tax_order[]").val(this.getId(e)),i.addClass("dashicons dashicons-menu cld-tax-order-list-item-handle"),t.append(i).append(e.name).append(n),t}}return e=>t(n,e)};wp.hooks.addFilter("editor.PostTaxonomyType","cld",i)}var p=u;const m={wpWrap:document.getElementById("wpwrap"),wpContent:document.getElementById("wpbody-content"),libraryWrap:document.getElementById("cloudinary-embed"),_init:function(){let e=this;"undefined"!=typeof CLD_ML&&(cloudinary.openMediaLibrary(CLD_ML.mloptions,{insertHandler:function(e){alert("Import is not yet implemented.")}}),window.addEventListener("resize",(function(t){e._resize()})),e._resize())},_resize:function(){let e=getComputedStyle(this.wpContent);this.libraryWrap.style.height=this.wpWrap.offsetHeight-parseInt(e.getPropertyValue("padding-bottom"))+"px"}};var h=m;m._init();i(2);i.d(t,"cloudinary",(function(){return f}));window.$=window.jQuery;const f={settings:s.a,sync:r,widget:l.a,Global_Transformations:c,Terms_Order:p,Media_Library:h}}]); \ No newline at end of file +!function(e){var t={};function i(n){if(t[n])return t[n].exports;var s=t[n]={i:n,l:!1,exports:{}};return e[n].call(s.exports,s,s.exports,i),s.l=!0,s.exports}i.m=e,i.c=t,i.d=function(e,t,n){i.o(e,t)||Object.defineProperty(e,t,{enumerable:!0,get:n})},i.r=function(e){"undefined"!=typeof Symbol&&Symbol.toStringTag&&Object.defineProperty(e,Symbol.toStringTag,{value:"Module"}),Object.defineProperty(e,"__esModule",{value:!0})},i.t=function(e,t){if(1&t&&(e=i(e)),8&t)return e;if(4&t&&"object"==typeof e&&e&&e.__esModule)return e;var n=Object.create(null);if(i.r(n),Object.defineProperty(n,"default",{enumerable:!0,value:e}),2&t&&"string"!=typeof e)for(var s in e)i.d(n,s,function(t){return e[t]}.bind(null,s));return n},i.n=function(e){var t=e&&e.__esModule?function(){return e.default}:function(){return e};return i.d(t,"a",t),t},i.o=function(e,t){return Object.prototype.hasOwnProperty.call(e,t)},i.p="",i(i.s=3)}([function(e,t){window,jQuery,jQuery(document).ready((function(e){e(document).on("tabs.init",(function(){var t=e(".settings-tab-trigger"),i=e(".settings-tab-section");e(this).on("click",".settings-tab-trigger",(function(n){var s=e(this),a=e(s.attr("href"));n.preventDefault(),t.removeClass("active"),i.removeClass("active"),s.addClass("active"),a.addClass("active"),e(document).trigger("settings.tabbed",s)})),e(".cld-field").not('[data-condition="false"]').each((function(){const t=e(this),i=t.data("condition");for(let n in i){const s=i[n],a=e("#field-"+n),r=t.closest("tr");a.on("change init",(function(){this.value===s||this.checked?r.show():r.hide()})),a.trigger("init")}})),e("#field-cloudinary_url").on("input change",(function(){let t=e(this),i=t.val();new RegExp(/^(?:CLOUDINARY_URL=)?(cloudinary:\/\/){1}(\d)*[:]{1}[^:@]*[@]{1}[^@]*$/g).test(i)?(t.addClass("settings-valid-field"),t.removeClass("settings-invalid-field")):(t.removeClass("settings-valid-field"),t.addClass("settings-invalid-field"))})).trigger("change")})),e(".render-trigger[data-event]").each((function(){var t=e(this),i=t.data("event");t.trigger(i,this)}))}))},function(e,t){if(wp.media&&window.CLDN){wp.media.events.on("editor:image-edit",(function(e){e.metadata.cldoverwrite=null,e.image.className.split(" ").indexOf("cld-overwrite")>=0&&(e.metadata.cldoverwrite="true")})),wp.media.events.on("editor:image-update",(function(e){let t=e.image.className.split(" ");e.metadata.cldoverwrite&&-1===t.indexOf("cld-overwrite")?t.push("cld-overwrite"):!e.metadata.cldoverwrite&&t.indexOf("cld-overwrite")>=0&&delete t[t.indexOf("cld-overwrite")],e.image.className=t.join(" ")}));let e=null,t=wp.media.string.props;wp.media.string.props=function(i,n){return i.cldoverwrite&&(i.classes=["cld-overwrite"],e=!0),t(i,n)},wp.media.post=function(t,i){if("send-attachment-to-editor"===t){let t=wp.media.editor.get().state().get("selection").get(i.attachment);t.attributes.transformations&&(i.attachment.transformations=t.attributes.transformations),(i.html.indexOf("cld-overwrite")>-1||!0===e)&&(i.attachment.cldoverwrite=!0,e=null)}return wp.ajax.post(t,i)};wp.media.controller.Library;let i=wp.media.view.MediaFrame.Select,n=wp.media.view.MediaFrame.Post,s=wp.media.view.MediaFrame.ImageDetails,a=wp.media.view.MediaFrame.VideoDetails,r=wp.media.View.extend({tagName:"div",className:"cloudinary-widget",template:wp.template("cloudinary-dam"),active:!1,toolbar:null,frame:null,ready:function(){let e=this.controller,t=this.model.get("selection"),i=this.model.get("library"),n=wp.media.model.Attachment;if(CLDN.mloptions.multiple=e.options.multiple,this.cid!==this.active){if(CLDN.mloptions.inline_container="#cloudinary-dam-"+e.cid,1===t.length){var s=n.get(t.models[0].id);void 0!==s.attributes.public_id&&(CLDN.mloptions.asset={resource_id:s.attributes.public_id})}else CLDN.mloptions.asset=null;window.ml=cloudinary.openMediaLibrary(CLDN.mloptions,{insertHandler:function(s){for(let a=0;a=100&&void 0!==e.started?(this.submitButton.style.display=this.hide,this.stopButton.style.display=this.show):e.pending>0?(this.submitButton.style.display=this.show,this.stopButton.style.display=this.hide):e.processing>0?this.stopButton.style.display=this.show:this.stopButton.style.display=this.hide,e.percent<100?(this.barSyncCount.innerText=e.total,this.progressCount.innerText=e.done,this.progress.style.display=this.show):(this.completed.style.display=this.show,this.progress.style.display=this.hide)},_start:function(e){e.preventDefault(),a.stopButton.style.display=a.show,a.submitButton.style.display=a.hide,a.pushAttachments()},_reset:function(e){a.submitButton.style.display=a.hide,a.getStatus()},_init:function(e){"undefined"!=typeof cloudinaryApi&&((document.attachEvent?"complete"===document.readyState:"loading"!==document.readyState)?e():document.addEventListener("DOMContentLoaded",e))}};var r=a;a._init((function(){a._reset(),a.submitButton.addEventListener("click",a._start),a.stopButton.addEventListener("click",a.stopSync)}));var o=i(1),l=i.n(o);const d={sample:{image:document.getElementById("transformation-sample-image"),video:document.getElementById("transformation-sample-video")},preview:{image:document.getElementById("sample-image"),video:document.getElementById("sample-video")},fields:document.getElementsByClassName("cld-field"),button:{image:document.getElementById("refresh-image-preview"),video:document.getElementById("refresh-video-preview")},spinner:{image:document.getElementById("image-loader"),video:document.getElementById("video-loader")},activeItem:null,elements:{image:[],video:[]},_placeItem:function(e){null!==e&&(e.style.display="block",e.style.visibility="visible",e.style.position="absolute",e.style.top=e.parentElement.clientHeight/2-e.clientHeight/2+"px",e.style.left=e.parentElement.clientWidth/2-e.clientWidth/2+"px")},_setLoading:function(e){this.button[e].style.display="block",this._placeItem(this.button[e]),this.preview[e].style.opacity="0.1"},_build:function(e){this.sample[e].innerHTML="",this.elements[e]=[];for(let t of this.fields){if(e!==t.dataset.context)continue;let i=t.value.trim();if(i.length){if("select-one"===t.type){if("none"===i)continue;i=t.dataset.meta+"_"+i}else{let e=t.dataset.context;i=this._transformations(i,e,!0)}i&&this.elements[e].push(i)}}let t="";this.elements[e].length&&(t="/"+this.elements[e].join(",").replace(/ /g,"%20")),this.sample[e].textContent=t,this.sample[e].parentElement.href="https://res.cloudinary.com/demo/"+this.sample[e].parentElement.innerText.trim().replace("../","").replace(/ /g,"%20")},_clearLoading:function(e){this.spinner[e].style.visibility="hidden",this.activeItem=null,this.preview[e].style.opacity=1},_refresh:function(e,t){e&&e.preventDefault();let i=this,n=CLD_GLOBAL_TRANSFORMATIONS[t].preview_url+i.elements[t].join(",")+CLD_GLOBAL_TRANSFORMATIONS[t].file;if(this.button[t].style.display="none",this._placeItem(this.spinner[t]),"image"===t){let e=new Image;e.onload=function(){i.preview[t].src=this.src,i._clearLoading(t),e.remove()},e.onerror=function(){alert(CLD_GLOBAL_TRANSFORMATIONS[t].error),i._clearLoading(t)},e.src=n}else{let e=i._transformations(i.elements[t].join(","),t);samplePlayer.source({publicId:"dog",transformation:e}),i._clearLoading(t)}},_transformations:function(e,t,i=!1){let n=CLD_GLOBAL_TRANSFORMATIONS[t].valid_types,s=null,a=e.split("/"),r=[];for(let e=0;e{const n=!!i.length&&jQuery('[data-item="'+s+":"+i[0].id+'"]');n.length?n.remove():(jQuery(`.cld-tax-order-list-item:contains(${r})`).remove(),--e.startId),this.processTags(t)})}),jQuery("body").on("change",".selectit input",(function(){const t=jQuery(this),i=t.val(),n=t.is(":checked"),s=t.parent().text().trim();!0===n?e.tags.find(`[data-item="category:${i}"]`).length||e._pushItem(`category:${i}`,s):e.tags.find(`[data-item="category:${i}"]`).remove()}))},_createItem:function(e,t){const i=jQuery("
  • "),n=jQuery(""),s=jQuery("");return i.addClass("cld-tax-order-list-item").attr("data-item",e),s.addClass("cld-tax-order-list-item-input").attr("type","hidden").attr("name","cld_tax_order[]").val(e),n.addClass("dashicons dashicons-menu cld-tax-order-list-item-handle"),i.append(n).append(t).append(s),i},_pushItem:function(e,t){let i=this._createItem(e,t);this.tags.append(i)},_sortable:function(){jQuery(".cld-tax-order-list").sortable({connectWith:".cld-tax-order",axis:"y",handle:".cld-tax-order-list-item-handle",placeholder:"cld-tax-order-list-item-placeholder",forcePlaceholderSize:!0,helper:"clone"})}};if(void 0!==window.CLDN&&(u._init(),jQuery("[data-wp-lists] .selectit input[checked]").map((e,t)=>{jQuery(t).trigger("change")})),wp.data&&wp.data.select("core/editor")){const e={};wp.data.subscribe((function(){let t=wp.data.select("core").getTaxonomies();if(t)for(let i in t){const n=wp.data.select("core/editor").getEditedPostAttribute(t[i].rest_base);e[t[i].slug]=n}}));const t=wp.element.createElement,i=i=>{class n extends i{constructor(e){super(e),this.currentItems=jQuery(".cld-tax-order-list-item").map((e,t)=>jQuery(t).data("item")).get()}makeItem(e){if(this.currentItems.includes(this.getId(e)))return;const t=this.makeElement(e);jQuery("#cld-tax-items").append(t)}removeItem(e){const t=jQuery(`[data-item="${this.getId(e)}"]`);t.length&&(t.remove(),this.currentItems=this.currentItems.filter(t=>t!==this.getId(e)))}findOrCreateTerm(e){return(e=super.findOrCreateTerm(e)).then(e=>this.makeItem(e)),e}onChange(t){super.onChange(t);const i=this.pickItem(t);i&&(e[this.props.slug].includes(i.id)?this.makeItem(i):this.removeItem(i))}pickItem(e){if("object"==typeof e){if(e.target){for(let t in this.state.availableTerms)if(this.state.availableTerms[t].id===parseInt(e.target.value))return this.state.availableTerms[t]}else if(Array.isArray(e)){let t=this.state.selectedTerms.filter(t=>!e.includes(t))[0];return void 0===t&&(t=e.filter(e=>!this.state.selectedTerms.includes(e))[0]),this.state.availableTerms.find(e=>e.name===t)}}else if("number"==typeof e){for(let t in this.state.availableTerms)if(this.state.availableTerms[t].id===e)return this.state.availableTerms[t]}else{let t;if(e.length>this.state.selectedTerms.length)for(let i in e)-1===this.state.selectedTerms.indexOf(e[i])&&(t=e[i]);else for(let i in this.state.selectedTerms)-1===e.indexOf(this.state.selectedTerms[i])&&(t=this.state.selectedTerms[i]);for(let e in this.state.availableTerms)if(this.state.availableTerms[e].name===t)return this.state.availableTerms[e]}}getId(e){return`${this.props.slug}:${e.id}`}makeElement(e){const t=jQuery("
  • "),i=jQuery(""),n=jQuery("");return t.addClass("cld-tax-order-list-item").attr("data-item",this.getId(e)),n.addClass("cld-tax-order-list-item-input").attr("type","hidden").attr("name","cld_tax_order[]").val(this.getId(e)),i.addClass("dashicons dashicons-menu cld-tax-order-list-item-handle"),t.append(i).append(e.name).append(n),t}}return e=>t(n,e)};wp.hooks.addFilter("editor.PostTaxonomyType","cld",i)}var p=u;const m={wpWrap:document.getElementById("wpwrap"),wpContent:document.getElementById("wpbody-content"),libraryWrap:document.getElementById("cloudinary-embed"),_init:function(){let e=this;"undefined"!=typeof CLD_ML&&(cloudinary.openMediaLibrary(CLD_ML.mloptions,{insertHandler:function(e){alert("Import is not yet implemented.")}}),window.addEventListener("resize",(function(t){e._resize()})),e._resize())},_resize:function(){let e=getComputedStyle(this.wpContent);this.libraryWrap.style.height=this.wpWrap.offsetHeight-parseInt(e.getPropertyValue("padding-bottom"))+"px"}};var h=m;m._init();i(2);i.d(t,"cloudinary",(function(){return f}));window.$=window.jQuery;const f={settings:s.a,sync:r,widget:l.a,Global_Transformations:c,Terms_Order:p,Media_Library:h}}]); \ No newline at end of file From bbb6fba62e68919cefb4e68273cc8528959c290f Mon Sep 17 00:00:00 2001 From: David Cramer Date: Fri, 24 Apr 2020 13:30:39 +0200 Subject: [PATCH 03/20] add notice handling and ui on dashboard. --- .../php/class-connect.php | 90 +++++++++++++++---- .../ui-definitions/tabs/dashboard-content.php | 29 +++++- 2 files changed, 96 insertions(+), 23 deletions(-) diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-connect.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-connect.php index 5a9dd1f83..645a399e3 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-connect.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-connect.php @@ -61,6 +61,13 @@ class Connect implements Config, Setup, Notice { */ public $handle; + /** + * Holder of general notices. + * + * @var array + */ + protected $notices = array(); + /** * Initiate the plugin resources. * @@ -119,30 +126,30 @@ public function verify_connection( $data ) { if ( empty( $data['cloudinary_url'] ) ) { delete_option( 'cloudinary_connection_signature' ); - add_settings_error( - 'cloudinary_connect', - 'connection_error', - __( 'Connection to Cloudinary has been removed.', 'cloudinary' ), - 'notice-warning' + add_settings_error( + 'cloudinary_connect', + 'connection_error', + __( 'Connection to Cloudinary has been removed.', 'cloudinary' ), + 'notice-warning' ); return $data; } $data['cloudinary_url'] = str_replace( 'CLOUDINARY_URL=', '', $data['cloudinary_url'] ); - $current = $this->plugin->config['settings']['connect']; - + $current = $this->plugin->config['settings']['connect']; + if ( $current['cloudinary_url'] === $data['cloudinary_url'] ) { return $data; } // Pattern match to ensure validity of the provided url if ( ! preg_match( '~^(?:CLOUDINARY_URL=)?cloudinary://[0-9]+:[A-Za-z_0-9]+@[A-Za-z]+~', $data['cloudinary_url'] ) ) { - add_settings_error( - 'cloudinary_connect', - 'format_mismatch', - __( 'The environment variable URL must be in this format: cloudinary://API_KEY:API_SECRET@CLOUD_NAME', 'cloudinary' ), - 'error' + add_settings_error( + 'cloudinary_connect', + 'format_mismatch', + __( 'The environment variable URL must be in this format: cloudinary://API_KEY:API_SECRET@CLOUD_NAME', 'cloudinary' ), + 'error' ); return $current; @@ -152,6 +159,7 @@ public function verify_connection( $data ) { if ( ! empty( $result['message'] ) ) { add_settings_error( 'cloudinary_connect', $result['type'], $result['message'], 'error' ); + return $current; } @@ -304,7 +312,6 @@ public function setup() { } } $this->usage = $stats; - } } @@ -335,7 +342,7 @@ public function get_config() { } $data['cloudinary_url'] = str_replace( 'CLOUDINARY_URL=', '', $data['cloudinary_url'] ); - $test = $this->test_connection( $data['cloudinary_url'] ); + $test = $this->test_connection( $data['cloudinary_url'] ); if ( 'connection_success' === $test['type'] ) { $signature = md5( $data['cloudinary_url'] ); @@ -353,16 +360,61 @@ public function get_config() { return $signature; } + /** + * Set usage notices if limits are towards higher end. + */ + public function usage_notices() { + if ( ! empty( $this->usage ) ) { + foreach ( $this->usage as $stat => $values ) { + if ( ! is_array( $values ) || ! isset( $values['used_percent'] ) || $values['used_percent'] <= 0 ) { + continue; + } + if ( $values['used_percent'] >= 1 ) { + $link = null; + $link_text = null; + if ( 90 <= $values['used_percent'] ) { + // 90% used - show error. + $level = 'error'; + $link = 'https://cloudinary.com/console/lui/upgrade_options'; + $link_text = __( 'Upgrade Plan' ); + } elseif ( 80 <= $values['used_percent'] ) { + $level = 'warning'; + } elseif ( 70 <= $values['used_percent'] ) { + $level = 'neutral'; + } else { + continue; + } + // translators: Placeholders are URLS and percentage values. + $message = sprintf( + __( + ' Cloudinary Quota: %1$s at %2$s %4$s', + 'cloudinary' + ), + ucwords( $stat ), + $values['used_percent'] . '%', + $link, + $link_text + ); + $this->notices[] = array( + 'message' => $message, + 'type' => $level, + 'dismissible' => false, + ); + } + } + } + } + /** * Get admin notices. */ public function get_notices() { - $screen = get_current_screen(); - $notices = array(); + $this->usage_notices(); + $screen = get_current_screen(); if ( empty( $this->plugin->config['connect'] ) ) { if ( is_object( $screen ) && in_array( $screen->id, $this->plugin->components['settings']->handles, true ) ) { - $link = '' . __( 'Connect', 'cloudinary' ) . ' '; - $notices[] = array( + $link = '' . __( 'Connect', 'cloudinary' ) . ' '; + $this->notices[] = array( 'message' => $link . __( 'your Cloudinary account with WordPress to get started.', 'cloudinary' ), 'type' => 'error', 'dismissible' => true, @@ -370,7 +422,7 @@ public function get_notices() { } } - return $notices; + return $this->notices; } } diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/dashboard-content.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/dashboard-content.php index 2137dbeba..4bad4aab6 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/dashboard-content.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/dashboard-content.php @@ -6,7 +6,7 @@ */ $video_url = ''; // Left blank for when we get the final video URL. - +$usage = $this->plugin->components['connect']->usage; ?>
    @@ -27,6 +27,27 @@
    +
    +
    + | + + + | + + + + | + + + + + +
    +
    +
    + + +
    @@ -59,8 +80,8 @@
    From 687d3f36710ef6bf626f9d85e40fb40747313b63 Mon Sep 17 00:00:00 2001 From: David Cramer Date: Sat, 25 Apr 2020 07:25:16 +0200 Subject: [PATCH 04/20] improve consistancey on meta and allow switching between account types --- .../php/class-connect.php | 148 +++++++++++------- .../php/class-media.php | 6 +- .../php/sync/class-push-sync.php | 6 +- .../php/sync/class-upload-sync.php | 4 +- .../ui-definitions/tabs/dashboard-content.php | 36 ++++- 5 files changed, 130 insertions(+), 70 deletions(-) diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-connect.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-connect.php index 645a399e3..97706257e 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-connect.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-connect.php @@ -68,6 +68,19 @@ class Connect implements Config, Setup, Notice { */ protected $notices = array(); + /** + * Holds the meta keys for connect meta to maintain consistency. + */ + const META_KEYS = array( + 'usage' => '_cloudinary_usage', + 'last_usage' => '_cloudinary_last_usage', + 'signature' => 'cloudinary_connection_signature', + 'version' => 'cloudinary_version', + 'url' => 'cloudinary_url', + 'connect' => 'cloudinary_connect', + 'cache' => 'cloudinary_settings_cache', + ); + /** * Initiate the plugin resources. * @@ -124,7 +137,7 @@ public function media_library_script() { */ public function verify_connection( $data ) { if ( empty( $data['cloudinary_url'] ) ) { - delete_option( 'cloudinary_connection_signature' ); + delete_option( self::META_KEYS['signature'] ); add_settings_error( 'cloudinary_connect', @@ -164,7 +177,7 @@ public function verify_connection( $data ) { } add_settings_error( 'cloudinary_connect', 'connection_success', __( 'Successfully connected to Cloudinary.', 'cloudinary' ), 'updated' ); - update_option( 'cloudinary_connection_signature', md5( $data['cloudinary_url'] ) ); + update_option( self::META_KEYS['signature'], md5( $data['cloudinary_url'] ) ); return $data; } @@ -221,11 +234,14 @@ function ( $a ) { } $this->config_from_url( $url ); - $test = new Connect\Api( $this, $this->plugin->version ); - $test = $test->ping(); - if ( is_wp_error( $test ) ) { + $test = new Connect\Api( $this, $this->plugin->version ); + $test_result = $test->ping(); + if ( is_wp_error( $test_result ) ) { $result['type'] = 'connection_error'; - $result['message'] = ucwords( str_replace( '_', ' ', $test->get_error_message() ) ); + $result['message'] = ucwords( str_replace( '_', ' ', $test_result->get_error_message() ) ); + } else { + $this->api = $test; + $this->usage_stats( true ); } return $result; @@ -297,22 +313,34 @@ public function setup() { // Get the cloudinary url from plugin config. $config = $this->plugin->config['settings']['connect']; if ( ! empty( $config['cloudinary_url'] ) ) { - $this->config_from_url( $config['cloudinary_url'] ); - $this->api = new Connect\Api( $this, $this->plugin->version ); - $stats = get_transient( '_cloudinary_usage' ); - if ( empty( $stats ) ) { - // Get users plan. - $stats = $this->plugin->components['connect']->api->usage(); - if ( ! is_wp_error( $stats ) && ! empty( $stats['media_limits'] ) ) { - $stats['max_image_size'] = $stats['media_limits']['image_max_size_bytes']; - $stats['max_video_size'] = $stats['media_limits']['video_max_size_bytes']; - set_transient( '_cloudinary_usage', $stats, HOUR_IN_SECONDS ); - } + $this->usage_stats( true ); + } + } + + /** + * Set the usage stats from the Cloudinary API. + * + * @param bool $refresh Flag to force a refresh. + */ + public function usage_stats( $refresh = false ) { + $stats = get_transient( self::META_KEYS['usage'] ); + if ( empty( $stats ) || true === $refresh ) { + // Get users plan. + $stats = $this->api->usage(); + if ( ! is_wp_error( $stats ) && ! empty( $stats['media_limits'] ) ) { + $stats['max_image_size'] = $stats['media_limits']['image_max_size_bytes']; + $stats['max_video_size'] = $stats['media_limits']['video_max_size_bytes']; + set_transient( self::META_KEYS['usage'], $stats, HOUR_IN_SECONDS ); + update_option( self::META_KEYS['last_usage'], $stats );// Save the last successful call to prevent crashing. + } else { + // Handle error by logging and fetching the last success. + // @todo : log issue. + $stats = get_option( self::META_KEYS['last_usage'] ); } - $this->usage = $stats; } + $this->usage = $stats; } /** @@ -323,14 +351,14 @@ public function setup() { * @return array The array of the config options stored. */ public function get_config() { - $signature = get_option( 'cloudinary_connection_signature', null ); - $version = get_option( 'cloudinary_version' ); + $signature = get_option( self::META_KEYS['signature'], null ); + $version = get_option( self::META_KEYS['version'] ); if ( empty( $signature ) || version_compare( $this->plugin->version, $version, '>' ) ) { // Check if there's a previous version, or missing signature. - $cld_url = get_option( 'cloudinary_url', null ); + $cld_url = get_option( self::META_KEYS['url'], null ); if ( null === $cld_url ) { // Post V1. - $data = get_option( 'cloudinary_connect', array() ); + $data = get_option( self::META_KEYS['connect'], array() ); if ( ! isset( $data['cloudinary_url'] ) || empty( $data['cloudinary_url'] ) ) { return null; // return null to indicate not valid. } @@ -349,10 +377,10 @@ public function get_config() { // remove filters as we've already verified it and 'add_settings_error()' isin't available yet. remove_filter( 'pre_update_option_cloudinary_connect', array( $this, 'verify_connection' ) ); - update_option( 'cloudinary_connect', $data ); - update_option( 'cloudinary_connection_signature', $signature ); - update_option( 'cloudinary_version', $this->plugin->version ); - delete_option( 'cloudinary_settings_cache' ); // remove the cache. + update_option( self::META_KEYS['connect'], $data ); + update_option( self::META_KEYS['signature'], $signature ); + update_option( self::META_KEYS['version'], $this->plugin->version ); + delete_option( self::META_KEYS['cache'] ); // remove the cache. $this->plugin->config['settings']['connect'] = $data; // Set the connection url for this round. } } @@ -365,42 +393,46 @@ public function get_config() { */ public function usage_notices() { if ( ! empty( $this->usage ) ) { + $usage_type = 'used_percent'; + if ( isset( $this->usage['credits'] ) ) { + $usage_type = 'credits_usage'; + } foreach ( $this->usage as $stat => $values ) { - if ( ! is_array( $values ) || ! isset( $values['used_percent'] ) || $values['used_percent'] <= 0 ) { + + if ( ! is_array( $values ) || ! isset( $values[ $usage_type ] ) || 0 > $values[ $usage_type ] ) { continue; } - if ( $values['used_percent'] >= 1 ) { - $link = null; - $link_text = null; - if ( 90 <= $values['used_percent'] ) { - // 90% used - show error. - $level = 'error'; - $link = 'https://cloudinary.com/console/lui/upgrade_options'; - $link_text = __( 'Upgrade Plan' ); - } elseif ( 80 <= $values['used_percent'] ) { - $level = 'warning'; - } elseif ( 70 <= $values['used_percent'] ) { - $level = 'neutral'; - } else { - continue; - } - // translators: Placeholders are URLS and percentage values. - $message = sprintf( - __( - ' Cloudinary Quota: %1$s at %2$s %4$s', - 'cloudinary' - ), - ucwords( $stat ), - $values['used_percent'] . '%', - $link, - $link_text - ); - $this->notices[] = array( - 'message' => $message, - 'type' => $level, - 'dismissible' => false, - ); + + $link = null; + $link_text = null; + if ( 90 <= $values[ $usage_type ] ) { + // 90% used - show error. + $level = 'error'; + $link = 'https://cloudinary.com/console/lui/upgrade_options'; + $link_text = __( 'Upgrade Plan' ); + } elseif ( 80 <= $values[ $usage_type ] ) { + $level = 'warning'; + } elseif ( 70 <= $values[ $usage_type ] ) { + $level = 'neutral'; + } else { + continue; } + // translators: Placeholders are URLS and percentage values. + $message = sprintf( + __( + ' Cloudinary Quota: %1$s at %2$s %4$s', + 'cloudinary' + ), + ucwords( $stat ), + $values[ $usage_type ] . '%', + $link, + $link_text + ); + $this->notices[] = array( + 'message' => $message, + 'type' => $level, + 'dismissible' => false, + ); } } } diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-media.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-media.php index f91414f2a..9f0233445 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-media.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-media.php @@ -1078,9 +1078,9 @@ public function media_column_value( $column_name, $attachment_id ) { if ( false === $this->cloudinary_id( $attachment_id ) ) { // If false, lets check why by seeing if the file size is too large. $file = get_attached_file( $attachment_id ); // Get the file size to make sure it can exist in cloudinary. - $max_size = ( wp_attachment_is_image( $attachment_id ) ? 'max_image_size' : 'max_video_size' ); - if ( file_exists( $file ) && filesize( $file ) > $this->plugin->components['connect']->usage[ $max_size ] ) { - $max_size_hr = size_format( $this->plugin->components['connect']->usage[ $max_size ] ); + $max_size = ( wp_attachment_is_image( $attachment_id ) ? 'image_max_size_bytes' : 'video_max_size_bytes' ); + if ( file_exists( $file ) && filesize( $file ) > $this->plugin->components['connect']->usage['media_limits'][ $max_size ] ) { + $max_size_hr = size_format( $this->plugin->components['connect']->usage['media_limits'][ $max_size ] ); // translators: variable is file size. $status['note'] = sprintf( __( 'File size exceeds the maximum of %s. This media asset will be served from WordPress.', 'cloudinary' ), $max_size_hr ); $status['state'] = 'error'; diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-push-sync.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-push-sync.php index a1a9ae025..2c63aba0a 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-push-sync.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-push-sync.php @@ -356,10 +356,10 @@ public function prepare_upload( $post, $down_sync = false ) { } $resource_type = $this->get_resource_type( $post ); - $max_size = ( 'image' === $resource_type ? 'max_image_size' : 'max_video_size' ); + $max_size = ( 'image' === $resource_type ? 'image_max_size_bytes' : 'video_max_size_bytes' ); - if ( $file_size > $this->plugin->components['connect']->usage[ $max_size ] ) { - $max_size_hr = size_format( $this->plugin->components['connect']->usage[ $max_size ] ); + if ( $file_size > $this->plugin->components['connect']->usage['media_limits'][ $max_size ] ) { + $max_size_hr = size_format( $this->plugin->components['connect']->usage['media_limits'][ $max_size ] ); // translators: variable is file size. $error = sprintf( __( 'File size exceeds the maximum of %s. This media asset will be served from WordPress.', 'cloudinary' ), $max_size_hr ); $this->plugin->components['media']->delete_post_meta( $post->ID, Sync::META_KEYS['pending'] ); // Remove Flag. diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-sync.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-sync.php index 2c4bc7f62..140b91876 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-sync.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-sync.php @@ -114,10 +114,10 @@ public function prep_on_demand_upload( $cloudinary_id, $attachment_id ) { if ( $attachment_id && false === $cloudinary_id ) { // Check that this has not already been prepared for upload. if ( ! $this->is_pending( $attachment_id ) && apply_filters( 'cloudinary_on_demand_sync_enabled', $this->enabled ) ) { - $max_size = ( wp_attachment_is_image( $attachment_id ) ? 'max_image_size' : 'max_video_size' ); + $max_size = ( wp_attachment_is_image( $attachment_id ) ? 'image_max_size_bytes' : 'video_max_size_bytes' ); $file = get_attached_file( $attachment_id ); // Get the file size to make sure it can exist in cloudinary. - if ( file_exists( $file ) && filesize( $file ) < $this->plugin->components['connect']->usage[ $max_size ] ) { + if ( file_exists( $file ) && filesize( $file ) < $this->plugin->components['connect']->usage['media_limits'][ $max_size ] ) { $this->add_to_sync( $attachment_id ); } else { // Check if the src is a url. diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/dashboard-content.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/dashboard-content.php index 4bad4aab6..71233db23 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/dashboard-content.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/dashboard-content.php @@ -7,6 +7,27 @@ $video_url = ''; // Left blank for when we get the final video URL. $usage = $this->plugin->components['connect']->usage; +// Different account version have usage limits. +if ( isset( $usage['credits'] ) ) { + // New credit system. + $usage['credits'] = array( + 'limit' => $usage['credits']['limit'], + 'used_percent' => $usage['credits']['used_percent'], + ); + $usage['storage'] = array( + 'limit' => $usage['storage']['usage'], + 'used_percent' => $usage['storage']['credits_usage'], + ); + $usage['transformations'] = array( + 'limit' => $usage['transformations']['usage'], + 'used_percent' => $usage['transformations']['credits_usage'], + ); + $usage['bandwidth'] = array( + 'limit' => $usage['bandwidth']['usage'], + 'used_percent' => $usage['bandwidth']['credits_usage'], + ); +} + ?>
    @@ -30,15 +51,22 @@
    | - + + + + | + + + + | - + | - + @@ -53,7 +81,7 @@
    Image or Video Settings.', 'cloudinary' From 5526d0e9bc91859b38cce6bd5c4635848b9a6d19 Mon Sep 17 00:00:00 2001 From: David Cramer Date: Sat, 25 Apr 2020 07:28:34 +0200 Subject: [PATCH 05/20] clean up video js error --- .../ui-definitions/tabs/dashboard-content.php | 35 +++++++++---------- 1 file changed, 17 insertions(+), 18 deletions(-) diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/dashboard-content.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/dashboard-content.php index 71233db23..1e3ab94f7 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/dashboard-content.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/dashboard-content.php @@ -28,6 +28,16 @@ ); } +$manage_text = sprintf( + // translators: Placeholders are URLS. + __( + 'Manage Image or Video Settings.', + 'cloudinary' + ), + 'admin.php?page=cld_global_transformation', + 'admin.php?page=cld_global_transformation&tab=global_video_transformations' +); + ?>
    @@ -79,25 +89,14 @@
    - Image or Video Settings.', - 'cloudinary' - ), - 'admin.php?page=cld_global_transformation', - 'admin.php?page=cld_global_transformation&tab=global_video_transformations' - ); - - // Video Player for dashboard. - $player = array(); - $player[] = 'var cld = cloudinary.Cloudinary.new({ cloud_name: \'demo\' });'; - $player[] = 'var samplePlayer = cld.videoPlayer(\'dashboard-player\', { fluid : true } );'; - wp_add_inline_script( 'cld-player', implode( $player ) ); - - ?> +

    From 0cfbe8445c9b890532a8f2fa7d26cbb85409135c Mon Sep 17 00:00:00 2001 From: David Cramer Date: Fri, 8 May 2020 09:22:32 +0200 Subject: [PATCH 06/20] make method to get stat value. --- .../php/class-connect.php | 28 ++++++++++++ .../ui-definitions/tabs/dashboard-content.php | 44 +++++-------------- 2 files changed, 40 insertions(+), 32 deletions(-) diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-connect.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-connect.php index 97706257e..f2f5aadd1 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-connect.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-connect.php @@ -343,6 +343,34 @@ public function usage_stats( $refresh = false ) { $this->usage = $stats; } + /** + * Get a usage stat for display. + * + * @param string $type The type of stat to get. + * @param string|null $stat The stat to get. + * + * @return bool|string + */ + public function get_usage_stat( $type, $stat = null ) { + $value = false; + if ( isset( $this->usage[ $type ] ) ) { + if ( is_string( $this->usage[ $type ] ) ) { + $value = $this->usage[ $type ]; + } elseif ( is_array( $this->usage[ $type ] ) && isset( $this->usage[ $type ][ $stat ] ) ) { + $value = $this->usage[ $type ][ $stat ]; + } elseif ( is_array( $this->usage[ $type ] ) ) { + + if ( 'limit' === $stat && isset( $this->usage[ $type ]['usage'] ) ) { + $value = $this->usage[ $type ]['usage']; + } elseif ( 'used_percent' === $stat && isset( $this->usage[ $type ]['credits_usage'] ) ) { + $value = $this->usage[ $type ]['credits_usage']; + } + } + } + + return $value; + } + /** * Gets the config of a connection. * diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/dashboard-content.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/dashboard-content.php index 1e3ab94f7..1916d3322 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/dashboard-content.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/dashboard-content.php @@ -5,28 +5,8 @@ * @package Cloudinary */ -$video_url = ''; // Left blank for when we get the final video URL. -$usage = $this->plugin->components['connect']->usage; -// Different account version have usage limits. -if ( isset( $usage['credits'] ) ) { - // New credit system. - $usage['credits'] = array( - 'limit' => $usage['credits']['limit'], - 'used_percent' => $usage['credits']['used_percent'], - ); - $usage['storage'] = array( - 'limit' => $usage['storage']['usage'], - 'used_percent' => $usage['storage']['credits_usage'], - ); - $usage['transformations'] = array( - 'limit' => $usage['transformations']['usage'], - 'used_percent' => $usage['transformations']['credits_usage'], - ); - $usage['bandwidth'] = array( - 'limit' => $usage['bandwidth']['usage'], - 'used_percent' => $usage['bandwidth']['credits_usage'], - ); -} +$video_url = ''; // Left blank for when we get the final video URL. +$connection = $this->plugin->components['connect']; $manage_text = sprintf( // translators: Placeholders are URLS. @@ -60,25 +40,25 @@

    - | - + get_usage_stat( 'plan' ) ); ?> | + get_usage_stat( 'credits', 'limit' ) ) : ?> - - | + get_usage_stat( 'credits', 'limit' ) ) ); ?> + get_usage_stat( 'credits', 'used_percent' ) . '%' ); ?> | - - | + get_usage_stat( 'storage', 'limit' ) ) ); ?> + get_usage_stat( 'storage', 'used_percent' ) . '%' ); ?> | - - | + get_usage_stat( 'transformations', 'limit' ) ) ); ?> + get_usage_stat( 'transformations', 'used_percent' ) . '%' ); ?> | - - + get_usage_stat( 'bandwidth', 'limit' ) ) ); ?> + get_usage_stat( 'bandwidth', 'used_percent' ) . '%' ); ?>

    From 20399d25ff9c18779b44fa8dd1fb3c10ba714bd4 Mon Sep 17 00:00:00 2001 From: Marco Pereirinha Date: Wed, 13 May 2020 15:20:42 +0100 Subject: [PATCH 07/20] Fix a if condition that could stop a listing page. See CLOUD 409. --- .../php/sync/class-delete-sync.php | 3 ++- 1 file changed, 2 insertions(+), 1 deletion(-) diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-delete-sync.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-delete-sync.php index 4a85cc520..0d8c4f817 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-delete-sync.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-delete-sync.php @@ -65,7 +65,8 @@ public function can_delete_asset( $all_caps, $caps, $args ) { $has_error = $this->plugin->components['media']->get_post_meta( $post_id, Sync::META_KEYS['sync_error'], true ); if ( empty( $has_error ) ) { $all_caps['delete_posts'] = false; - if ( filter_input( INPUT_GET, 'action', FILTER_DEFAULT ) ) { + $action = filter_input( INPUT_GET, 'action', FILTER_SANITIZE_STRING ); + if ( ! empty( $action ) && '-1' !== $action ) { wp_die( esc_html__( 'Sorry, you can’t delete an asset until it has fully synced with Cloudinary. Try again once syncing is complete.', 'cloudinary' ) ); } } From 547645e94a975d848439253a9e8a3235016c384c Mon Sep 17 00:00:00 2001 From: Marco Pereirinha Date: Thu, 14 May 2020 17:33:44 +0100 Subject: [PATCH 08/20] Replace the bulk sync status feedback script --- .../js/src/components/sync.js | 24 ++++++++++++------- 1 file changed, 16 insertions(+), 8 deletions(-) diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/js/src/components/sync.js b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/js/src/components/sync.js index 941580985..e08df5416 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/js/src/components/sync.js +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/js/src/components/sync.js @@ -4,11 +4,10 @@ const Sync = { progress: document.getElementById( 'progress-wrapper' ), submitButton: document.getElementById( 'submit' ), stopButton: document.getElementById( 'stop-sync' ), - progressCount: document.getElementById( 'sync-progress' ), - barSyncCount: document.getElementById( 'sync-total' ), completed: document.getElementById( 'completed-notice' ), show: 'inline-block', hide: 'none', + isRunning: false, getStatus: function getStatus() { var self = this, resourceType = [], @@ -22,8 +21,9 @@ const Sync = { request.setRequestHeader( 'X-WP-Nonce', cloudinaryApi.nonce ); }, } ).done( function( data ) { - if ( data.done < data.total ) { - setTimeout( Sync.getStatus, 2000 ); + Sync.isRunning = data.is_running; + if ( Sync.isRunning ) { + setTimeout( Sync.getStatus, 10000 ); } Sync._updateUI( data ); } ); @@ -32,6 +32,8 @@ const Sync = { var self = this, url = cloudinaryApi.restUrl + 'cloudinary/v1/sync'; + Sync.isRunning = false; + wp.ajax.send( { url: url, data: { @@ -48,11 +50,16 @@ const Sync = { var self = this, url = cloudinaryApi.restUrl + 'cloudinary/v1/sync'; + Sync.isRunning = true; + Sync.progress.style.display = Sync.show; + wp.ajax.send( { url: url, beforeSend: function( request ) { request.setRequestHeader( 'X-WP-Nonce', cloudinaryApi.nonce ); }, + } ).done( function ( data ) { + setTimeout( Sync.getStatus, 10000 ); } ); }, _updateUI: function _updateUI( data ) { @@ -75,13 +82,14 @@ const Sync = { this.stopButton.style.display = this.hide; } - if ( data.percent < 100 ) { - this.barSyncCount.innerText = data.total; - this.progressCount.innerText = data.done; + if ( data.percent === 100 ) { + this.completed.style.display = this.show; + } + + if ( this.isRunning ) { this.progress.style.display = this.show; } else { - this.completed.style.display = this.show; this.progress.style.display = this.hide; } }, From e41b014e9d7e21b578779899c8540bca5ef8e78d Mon Sep 17 00:00:00 2001 From: Marco Pereirinha Date: Thu, 14 May 2020 17:34:16 +0100 Subject: [PATCH 09/20] Improve consistency --- .../php/sync/class-upload-queue.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-queue.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-queue.php index 6d0b77683..9260630ba 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-queue.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-queue.php @@ -37,7 +37,7 @@ class Upload_Queue { * * @var bool */ - private $running = null; + private $running = false; /** * Upload_Queue constructor. @@ -127,7 +127,7 @@ public function mark( $id, $type = 'done' ) { * @return bool */ public function is_running() { - if ( null === $this->running ) { + if ( false === $this->running ) { $queue = $this->get_queue(); $this->running = empty( $queue['started'] ) ? false : true; } From c79963d10cc56e3906d14c01a97db44d1846c997 Mon Sep 17 00:00:00 2001 From: Marco Pereirinha Date: Thu, 14 May 2020 17:34:47 +0100 Subject: [PATCH 10/20] Add running flag to the REST response --- .../php/sync/class-upload-queue.php | 2 ++ 1 file changed, 2 insertions(+) diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-queue.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-queue.php index 9260630ba..e76dbedae 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-queue.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-queue.php @@ -175,6 +175,8 @@ public function get_queue_status() { $this->stop_queue(); } + $return['is_running'] = $this->is_running(); + return $return; } From c9d6735f551368ab323e2ce2bc103ccf6f40c96c Mon Sep 17 00:00:00 2001 From: Marco Pereirinha Date: Thu, 14 May 2020 17:35:04 +0100 Subject: [PATCH 11/20] Add loading icon --- .../css/loading.svg | 21 +++++++++++++++++++ 1 file changed, 21 insertions(+) create mode 100644 cloudinary-image-management-and-manipulation-in-the-cloud-cdn/css/loading.svg diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/css/loading.svg b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/css/loading.svg new file mode 100644 index 000000000..0cf4e763f --- /dev/null +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/css/loading.svg @@ -0,0 +1,21 @@ + + + + + + + + + + + + From f06bcea4a3f3689d86769babd73a90bf5725d261 Mon Sep 17 00:00:00 2001 From: Marco Pereirinha Date: Thu, 14 May 2020 17:35:37 +0100 Subject: [PATCH 12/20] Replace the out of status by the simple syncing icon --- .../ui-definitions/tabs/sync-media-footer.php | 5 ++++- 1 file changed, 4 insertions(+), 1 deletion(-) diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/sync-media-footer.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/sync-media-footer.php index 509472490..6bbf1d7c8 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/sync-media-footer.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/sync-media-footer.php @@ -26,7 +26,10 @@ - / + + <?php esc_attr_e( 'Syncing…', 'cloudinary' ); ?> + +
    From f696a047c48df67c12551c3f82bc798008bfb185 Mon Sep 17 00:00:00 2001 From: David Cramer Date: Tue, 19 May 2020 12:31:27 +0200 Subject: [PATCH 13/20] update texts and remove forced reload. --- .../php/class-connect.php | 8 +++++--- 1 file changed, 5 insertions(+), 3 deletions(-) diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-connect.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-connect.php index 7a2e9b50e..90b15c803 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-connect.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-connect.php @@ -315,7 +315,7 @@ public function setup() { if ( ! empty( $config['cloudinary_url'] ) ) { $this->config_from_url( $config['cloudinary_url'] ); $this->api = new Connect\Api( $this, $this->plugin->version ); - $this->usage_stats( true ); + $this->usage_stats(); } } @@ -448,18 +448,20 @@ public function usage_notices() { // 90% used - show error. $level = 'error'; $link = 'https://cloudinary.com/console/lui/upgrade_options'; - $link_text = __( 'Upgrade Plan' ); + $link_text = __( 'upgrade your account', 'cloudinary' ); } elseif ( 80 <= $values[ $usage_type ] ) { $level = 'warning'; + $link_text = __( 'upgrade your account', 'cloudinary' ); } elseif ( 70 <= $values[ $usage_type ] ) { $level = 'neutral'; + $link_text = __( 'upgrade your account', 'cloudinary' ); } else { continue; } // translators: Placeholders are URLS and percentage values. $message = sprintf( __( - ' Cloudinary Quota: %1$s at %2$s %4$s', + ' You are %2$s of the way through your monthly quota for %1$s on your Cloudinary account. If you exceed your quota, the Cloudinary plugin will be deactivated until your next billing cycle and your media assets will be served from your WordPress Media Library. You may wish to %4$s and increase your quota to ensure you maintain full functionality.', 'cloudinary' ), ucwords( $stat ), From 5760d7bb47e27f74a9e33d68d565824d6a7ff173 Mon Sep 17 00:00:00 2001 From: Marco Pereirinha Date: Tue, 19 May 2020 15:15:39 +0100 Subject: [PATCH 14/20] Update loading url --- .../ui-definitions/tabs/sync-media-footer.php | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/sync-media-footer.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/sync-media-footer.php index 6bbf1d7c8..63a2da3c2 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/sync-media-footer.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/ui-definitions/tabs/sync-media-footer.php @@ -27,7 +27,7 @@ - <?php esc_attr_e( 'Syncing…', 'cloudinary' ); ?> + <?php esc_attr_e( 'Syncing…', 'cloudinary' ); ?> From 397ee44e5cabcf4c5dd871892203c9fa93a5d0ab Mon Sep 17 00:00:00 2001 From: Marco Pereirinha Date: Tue, 26 May 2020 10:10:16 +0100 Subject: [PATCH 15/20] Check vars before use them --- .../php/class-media.php | 5 ++++- .../php/sync/class-push-sync.php | 2 +- .../php/sync/class-upload-sync.php | 2 +- 3 files changed, 6 insertions(+), 3 deletions(-) diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-media.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-media.php index cd966dc35..737e09088 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-media.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/class-media.php @@ -574,7 +574,10 @@ public function cloudinary_url( $attachment_id, $size = array(), $transformation // Check size and correct if string or size. if ( is_string( $size ) || ( is_array( $size ) && 3 === count( $size ) ) ) { $intermediate = image_get_intermediate_size( $attachment_id, $size ); - $size = $this->get_crop( $intermediate['url'], $attachment_id ); + if ( ! is_array( $intermediate ) ) { + return false; + } + $size = $this->get_crop( $intermediate['url'], $attachment_id ); } /** diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-push-sync.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-push-sync.php index f69020e31..90e0b0779 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-push-sync.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-push-sync.php @@ -358,7 +358,7 @@ public function prepare_upload( $post, $down_sync = false ) { $resource_type = $this->get_resource_type( $post ); $max_size = ( 'image' === $resource_type ? 'max_image_size' : 'max_video_size' ); - if ( $file_size > $this->plugin->components['connect']->usage[ $max_size ] ) { + if ( ! empty( $this->plugin->components['connect']->usage[ $max_size ] ) && $file_size > $this->plugin->components['connect']->usage[ $max_size ] ) { $max_size_hr = size_format( $this->plugin->components['connect']->usage[ $max_size ] ); // translators: variable is file size. $error = sprintf( __( 'File size exceeds the maximum of %s. This media asset will be served from WordPress.', 'cloudinary' ), $max_size_hr ); diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-sync.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-sync.php index 2c4bc7f62..8187af545 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-sync.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-sync.php @@ -117,7 +117,7 @@ public function prep_on_demand_upload( $cloudinary_id, $attachment_id ) { $max_size = ( wp_attachment_is_image( $attachment_id ) ? 'max_image_size' : 'max_video_size' ); $file = get_attached_file( $attachment_id ); // Get the file size to make sure it can exist in cloudinary. - if ( file_exists( $file ) && filesize( $file ) < $this->plugin->components['connect']->usage[ $max_size ] ) { + if ( ! empty( $this->plugin->components['connect']->usage[ $max_size ] ) && file_exists( $file ) && filesize( $file ) < $this->plugin->components['connect']->usage[ $max_size ] ) { $this->add_to_sync( $attachment_id ); } else { // Check if the src is a url. From 1fe6402b7364ff18c01b57386f736109cd23ca62 Mon Sep 17 00:00:00 2001 From: Marco Pereirinha Date: Tue, 26 May 2020 10:10:38 +0100 Subject: [PATCH 16/20] Try to set SVGs size --- .../php/media/class-filter.php | 41 +++++++++++++++++++ 1 file changed, 41 insertions(+) diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/media/class-filter.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/media/class-filter.php index 5c2b0890a..553b4117a 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/media/class-filter.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/media/class-filter.php @@ -671,6 +671,45 @@ public function filter_image_block_pre_render( $block, $source_block ) { return $block; } + /** + * Attempt to set the width and height for SVGs. + * + * @param array|false $image The image details. + * @param int $attachment_id The attachment ID. + * @param string|int[] $size The requested image size. + * + * @return array|false + */ + public function filter_svg_image_size( $image, $attachment_id, $size ) { + if ( is_array( $image ) && preg_match('/\.svg$/i', $image[0] ) && $image[1] <= 1 ) { + $image[1] = $image[2] = null; + + if ( is_array( $size ) ) { + $image[1] = $size[0]; + $image[2] = $size[1]; + } elseif ( false !== ( $xml = simplexml_load_file( $image[0] ) ) ) { + $attr = $xml->attributes(); + $viewbox = explode( ' ', $attr->viewBox ); + + // Get width + if ( isset( $attr->width ) && preg_match( '/\d+/', $attr->width, $value ) ) { + $image[1] = (int) $value[0]; + } elseif ( 4 === count( $viewbox ) ) { + $image[1] = (int) $viewbox[2]; + } + + // Get height + if ( isset( $attr->height ) && preg_match( '/\d+/', $attr->height, $value ) ) { + $image[2] = (int) $value[0]; + } elseif ( 4 === count( $viewbox ) ) { + $image[2] = (int) $viewbox[3]; + } + } + } + + return $image; + } + /** * Setup hooks for the filters. */ @@ -709,5 +748,7 @@ function ( $type ) use ( $filter ) { // Filter for block rendering. add_filter( 'render_block_data', array( $this, 'filter_image_block_pre_render' ), 10, 2 ); + // Try to get SVGs size. + add_filter( 'wp_get_attachment_image_src', array( $this, 'filter_svg_image_size' ), 10, 3 ); } } From 6572de6a848328a55df2d0c435606de45021dd15 Mon Sep 17 00:00:00 2001 From: Marco Pereirinha Date: Tue, 26 May 2020 16:47:51 +0100 Subject: [PATCH 17/20] Move the queue resume to the shutdown --- .../php/sync/class-push-sync.php | 35 +++++++++++++++---- 1 file changed, 28 insertions(+), 7 deletions(-) diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-push-sync.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-push-sync.php index f69020e31..8289e17cf 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-push-sync.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-push-sync.php @@ -40,6 +40,13 @@ class Push_Sync { */ private $sync_types; + /** + * Holds the ID of the last attachment synced. + * + * @var int + */ + protected $post_id; + /** * Push_Sync constructor. * @@ -200,19 +207,33 @@ public function rest_push_attachments( \WP_REST_Request $request ) { if ( ! $this->plugin->components['sync']->managers['queue']->is_running() ) { // Check it wasn't stopped. return $this->rest_get_queue_status(); } - $post_id = $this->plugin->components['sync']->managers['queue']->get_post(); + + $this->post_id = $this->plugin->components['sync']->managers['queue']->get_post(); + // No post, end of queue. - if ( empty( $post_id ) ) { + if ( empty( $this->post_id ) ) { $this->plugin->components['sync']->managers['queue']->stop_queue(); return $this->rest_get_queue_status(); } + add_action( 'shutdown', array( $this, 'resume_queue' ) ); + + return $this->rest_get_queue_status(); + } + + /** + * Resume the bulk sync. + * + * @return bool|\WP_REST_Response + */ + public function resume_queue() { // Check if there is a Cloudinary ID in case this was synced on-demand before being processed by the queue. add_filter( 'cloudinary_on_demand_sync_enabled', '__return_false' ); // Disable the on-demand sync since we want the status. add_filter( 'cloudinary_id', '__return_false' ); // Disable the on-demand sync since we want the status. - if ( false === $this->plugin->components['media']->cloudinary_id( $post_id ) ) { - $stat = $this->push_attachments( array( $post_id ) ); + + if ( false === $this->plugin->components['media']->cloudinary_id( $this->post_id ) ) { + $stat = $this->push_attachments( array( $this->post_id ) ); if ( ! empty( $stat['processed'] ) ) { $result = 'done'; } else { @@ -226,8 +247,7 @@ public function rest_push_attachments( \WP_REST_Request $request ) { $result = 'done'; } - return $this->call_thread( $post_id, $result ); - + return $this->call_thread( $this->post_id, $result ); } /** @@ -246,7 +266,8 @@ private function call_thread( $last_id = null, $last_result = null ) { $params['last_id'] = $last_id; $params['last_result'] = $last_result; } - // Setup background call to cintinue the queue. + + // Setup background call to continue the queue. $this->plugin->components['api']->background_request( 'process', $params ); return $this->rest_get_queue_status(); From 7b3d9f7dc72f9c99dd939b68db36c62be6a4cb58 Mon Sep 17 00:00:00 2001 From: Marco Pereirinha Date: Tue, 26 May 2020 17:02:19 +0100 Subject: [PATCH 18/20] Add a fallback cron job that ensures that the queue is resumed --- .../php/sync/class-upload-queue.php | 60 +++++++++++++++++-- 1 file changed, 56 insertions(+), 4 deletions(-) diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-queue.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-queue.php index 6d0b77683..c21f4391a 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-queue.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-queue.php @@ -39,6 +39,20 @@ class Upload_Queue { */ private $running = null; + /** + * The cron frequency to ensure that the queue is progressing. + * + * @var int + */ + protected $cron_frequency; + + /** + * The cron offset since the last update. + * + * @var int + */ + protected $cron_start_offset; + /** * Upload_Queue constructor. * @@ -46,6 +60,20 @@ class Upload_Queue { */ public function __construct( \Cloudinary\Plugin $plugin ) { $this->plugin = $plugin; + + $this->cron_frequency = apply_filters( 'cloudinary_cron_frequency', 600 ); + $this->cron_start_offset = apply_filters( 'cloudinary_cron_start_offset', 60 ); + + $this->load_hooks(); + } + + /** + * Load the Upload Queue hooks. + * + * @return void + */ + public function load_hooks() { + add_action( 'cloudinary_resume_queue', array( $this, 'maybe_resume_queue' ) ); } /** @@ -85,6 +113,7 @@ public function get_post() { if ( ! empty( $queue['pending'] ) ) { $id = array_shift( $queue['pending'] ); $queue['processing'][] = $id; + $queue['last_update'] = current_time( 'timestamp' ); $this->set_queue( $queue ); } } @@ -209,7 +238,6 @@ public function build_queue() { // Transform attachments. $return = array( 'pending' => array(), - 'large' => array(), 'done' => array(), 'processing' => array(), 'error' => array(), @@ -233,17 +261,41 @@ public function stop_queue() { $this->set_queue( $queue ); } $this->running = false; - } + wp_clear_scheduled_hook( 'cloudinary_resume_queue' ); + } /** - * Startthe queue by setting the started flag. + * Start the queue by setting the started flag. + * + * @return void */ public function start_queue() { $queue = $this->get_queue(); - $queue['started'] = current_time( 'timestamp' ); + $queue['started'] = $queue['last_update'] = current_time( 'timestamp' ); $this->set_queue( $queue ); $this->running = true; + + if ( ! wp_next_scheduled( 'cloudinary_resume_queue' ) ) { + wp_schedule_single_event( time() + $this->cron_frequency, 'cloudinary_resume_queue' ); + } } + /** + * Maybe resume the queue. + * This is a fallback mechanism to resume the queue when it stops unexpectedly. + * + * @return void + */ + public function maybe_resume_queue() { + $now = current_time( 'timestamp' ); + $queue = $this->get_queue(); + + + if ( $now - $queue['last_update'] > $this->cron_start_offset ) { + $this->plugin->components['api']->background_request( 'process', array() ); + } + + wp_schedule_single_event( $now + $this->cron_frequency, 'cloudinary_resume_queue' ); + } } From 1a9d9fd5ef17388b63dfb3e96eca59129870022e Mon Sep 17 00:00:00 2001 From: Marco Pereirinha Date: Wed, 27 May 2020 14:14:54 +0100 Subject: [PATCH 19/20] Use constants for better readability --- .../php/sync/class-upload-queue.php | 4 ++-- 1 file changed, 2 insertions(+), 2 deletions(-) diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-queue.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-queue.php index c21f4391a..e1b86e5a9 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-queue.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-queue.php @@ -61,8 +61,8 @@ class Upload_Queue { public function __construct( \Cloudinary\Plugin $plugin ) { $this->plugin = $plugin; - $this->cron_frequency = apply_filters( 'cloudinary_cron_frequency', 600 ); - $this->cron_start_offset = apply_filters( 'cloudinary_cron_start_offset', 60 ); + $this->cron_frequency = apply_filters( 'cloudinary_cron_frequency', 10 * MINUTE_IN_SECONDS ); + $this->cron_start_offset = apply_filters( 'cloudinary_cron_start_offset', MINUTE_IN_SECONDS ); $this->load_hooks(); } From 24990f40747f325633d584069a1e0fe72a581d2c Mon Sep 17 00:00:00 2001 From: Marco Pereirinha Date: Wed, 27 May 2020 14:16:21 +0100 Subject: [PATCH 20/20] Check if the queue is running --- .../php/sync/class-upload-queue.php | 3 +-- 1 file changed, 1 insertion(+), 2 deletions(-) diff --git a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-queue.php b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-queue.php index e1b86e5a9..a6599fe99 100644 --- a/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-queue.php +++ b/cloudinary-image-management-and-manipulation-in-the-cloud-cdn/php/sync/class-upload-queue.php @@ -291,8 +291,7 @@ public function maybe_resume_queue() { $now = current_time( 'timestamp' ); $queue = $this->get_queue(); - - if ( $now - $queue['last_update'] > $this->cron_start_offset ) { + if ( $now - $queue['last_update'] > $this->cron_start_offset && $this->is_running() ) { $this->plugin->components['api']->background_request( 'process', array() ); }