]> BookStack Code Mirror - bookstack/commitdiff
Got image uploads working
authorDan Brown <redacted>
Mon, 13 Jul 2015 20:52:56 +0000 (21:52 +0100)
committerDan Brown <redacted>
Mon, 13 Jul 2015 20:52:56 +0000 (21:52 +0100)
.gitignore
app/Http/Controllers/ImageController.php [new file with mode: 0644]
app/Http/routes.php
app/Image.php [new file with mode: 0644]
bootstrap/cache/.gitignore [changed mode: 0644->0755]
composer.json
composer.lock
config/app.php
database/migrations/2015_07_13_172121_create_images_table.php [new file with mode: 0644]
resources/assets/sass/_text.scss
resources/views/pages/edit.blade.php

index e5011ccbc6e671904da35c78571ae7c13de74f4f..9a50d01726c4abe6b6e5c47105d6b5cd1d39250b 100644 (file)
@@ -5,4 +5,5 @@ Homestead.yaml
 /public/dist
 .idea
 /public/plugins
-/public/css
\ No newline at end of file
+/public/css
+/storage/images
\ No newline at end of file
diff --git a/app/Http/Controllers/ImageController.php b/app/Http/Controllers/ImageController.php
new file mode 100644 (file)
index 0000000..941f2ad
--- /dev/null
@@ -0,0 +1,89 @@
+<?php
+
+namespace Oxbow\Http\Controllers;
+
+use Illuminate\Filesystem\Filesystem as File;
+use Illuminate\Http\Request;
+
+use Oxbow\Http\Requests;
+use Oxbow\Image;
+
+class ImageController extends Controller
+{
+    protected $image;
+    protected $file;
+
+    /**
+     * ImageController constructor.
+     * @param Image $image
+     * @param File $file
+     */
+    public function __construct(Image $image, File $file)
+    {
+        $this->image = $image;
+        $this->file = $file;
+    }
+
+    /**
+     * Returns an image from behind the public-facing application.
+     * @param Request $request
+     * @return \Illuminate\Http\Response
+     */
+    public function getImage(Request $request)
+    {
+        $cacheTime = 60*60*24;
+        $path = storage_path() . '/' . $request->path();
+        $modifiedTime = $this->file->lastModified($path);
+        $eTag = md5($modifiedTime . $path);
+        $headerLastModified = gmdate('r', $modifiedTime);
+        $headerExpires = gmdate('r', $modifiedTime + $cacheTime);
+
+        $headers = [
+            'Last-Modified' => $headerLastModified,
+            'Cache-Control' => 'must-revalidate',
+            'Pragma' => 'public',
+            'Expires' => $headerExpires,
+            'Etag' => $eTag
+        ];
+
+        $browserModifiedSince = $request->header('If-Modified-Since');
+        $browserNoneMatch = $request->header('If-None-Match');
+        if($browserModifiedSince !== null && file_exists($path) && ($browserModifiedSince == $headerLastModified || $browserNoneMatch == $eTag)) {
+            return response()->make('', 304, $headers);
+        }
+
+        if(file_exists($path)) {
+            return response()->make(file_get_contents($path), 200, array_merge($headers, [
+                'Content-Type' => $this->file->mimeType($path),
+                'Content-Length' => filesize($path),
+            ]));
+        }
+        abort(404);
+    }
+
+    /**
+     * Handles image uploads for use on pages.
+     * @param Request $request
+     * @return \Illuminate\Http\JsonResponse
+     */
+    public function upload(Request $request)
+    {
+        $imageUpload = $request->file('file');
+        $name = $imageUpload->getClientOriginalName();
+        $imagePath = '/images/' . Date('Y-m-M') . '/';
+        $storagePath = storage_path(). $imagePath;
+        $fullPath = $storagePath . $name;
+        while(file_exists($fullPath)) {
+            $name = substr(sha1(rand()), 0, 3) . $name;
+            $fullPath = $storagePath . $name;
+        }
+        $imageUpload->move($storagePath, $name);
+        // Create and save image object
+        $this->image->name = $name;
+        $this->image->url = $imagePath . $name;
+        $this->image->save();
+        return response()->json(['link' => $this->image->url]);
+    }
+
+
+}
index ec9cb7c6f4bcf9c0b62d0ecce9147d0fc2d0d81d..8840a62d5ef768cce8530bf633cbf8a84344feee 100644 (file)
@@ -29,6 +29,10 @@ Route::group(['prefix' => 'books'], function() {
     Route::put('/{bookSlug}/{pageSlug}', 'PageController@update');
 });
 
+Route::post('/upload/image', 'ImageController@upload');
+
+Route::get('/images/{any}', 'ImageController@getImage')->where('any', '.*');
+
 Route::get('/', function () {
     return view('base');
 });
diff --git a/app/Image.php b/app/Image.php
new file mode 100644 (file)
index 0000000..4600e5b
--- /dev/null
@@ -0,0 +1,10 @@
+<?php
+
+namespace Oxbow;
+
+use Illuminate\Database\Eloquent\Model;
+
+class Image extends Model
+{
+    //
+}
old mode 100644 (file)
new mode 100755 (executable)
index 264c2d75391a9aef06258dcb04896f93e7d8851d..f53ccf67dcf28dd71c7af1407b25c15b4e92117a 100644 (file)
@@ -6,7 +6,8 @@
     "type": "project",
     "require": {
         "php": ">=5.5.9",
-        "laravel/framework": "5.1.*"
+        "laravel/framework": "5.1.*",
+        "intervention/image": "^2.3"
     },
     "require-dev": {
         "fzaninotto/faker": "~1.4",
index 4d9f5869c3a9ed14228b0ff1f586e03e0b4a5891..79eb195ed0d429beb3934138b719b1d6641e39d6 100644 (file)
@@ -4,7 +4,7 @@
         "Read more about it at https://getcomposer.org/doc/01-basic-usage.md#composer-lock-the-lock-file",
         "This file is @generated automatically"
     ],
-    "hash": "5c6026b96e6fa11a641b51a6ba976f5e",
+    "hash": "f1c04613ce972bfab5c142cb0b588385",
     "packages": [
         {
             "name": "classpreloader/classpreloader",
             ],
             "time": "2014-12-20 21:24:13"
         },
+        {
+            "name": "guzzlehttp/psr7",
+            "version": "1.1.0",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/guzzle/psr7.git",
+                "reference": "af0e1758de355eb113917ad79c3c0e3604bce4bd"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/guzzle/psr7/zipball/af0e1758de355eb113917ad79c3c0e3604bce4bd",
+                "reference": "af0e1758de355eb113917ad79c3c0e3604bce4bd",
+                "shasum": ""
+            },
+            "require": {
+                "php": ">=5.4.0",
+                "psr/http-message": "~1.0"
+            },
+            "provide": {
+                "psr/http-message-implementation": "1.0"
+            },
+            "require-dev": {
+                "phpunit/phpunit": "~4.0"
+            },
+            "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "1.0-dev"
+                }
+            },
+            "autoload": {
+                "psr-4": {
+                    "GuzzleHttp\\Psr7\\": "src/"
+                },
+                "files": [
+                    "src/functions.php"
+                ]
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "MIT"
+            ],
+            "authors": [
+                {
+                    "name": "Michael Dowling",
+                    "email": "[email protected]",
+                    "homepage": "https://github.com/mtdowling"
+                }
+            ],
+            "description": "PSR-7 message implementation",
+            "keywords": [
+                "http",
+                "message",
+                "stream",
+                "uri"
+            ],
+            "time": "2015-06-24 19:55:15"
+        },
+        {
+            "name": "intervention/image",
+            "version": "2.3.1",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/Intervention/image.git",
+                "reference": "156f9d6f8a186c68b92f0c50084718f02dae1b5f"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/Intervention/image/zipball/156f9d6f8a186c68b92f0c50084718f02dae1b5f",
+                "reference": "156f9d6f8a186c68b92f0c50084718f02dae1b5f",
+                "shasum": ""
+            },
+            "require": {
+                "ext-fileinfo": "*",
+                "guzzlehttp/psr7": "~1.1",
+                "php": ">=5.4.0"
+            },
+            "require-dev": {
+                "mockery/mockery": "~0.9.2",
+                "phpunit/phpunit": "3.*"
+            },
+            "suggest": {
+                "ext-gd": "to use GD library based image processing.",
+                "ext-imagick": "to use Imagick based image processing.",
+                "intervention/imagecache": "Caching extension for the Intervention Image library"
+            },
+            "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "2.3-dev"
+                }
+            },
+            "autoload": {
+                "psr-4": {
+                    "Intervention\\Image\\": "src/Intervention/Image"
+                }
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "MIT"
+            ],
+            "authors": [
+                {
+                    "name": "Oliver Vogel",
+                    "email": "[email protected]",
+                    "homepage": "http://olivervogel.net/"
+                }
+            ],
+            "description": "Image handling and manipulation library with support for Laravel integration",
+            "homepage": "http://image.intervention.io/",
+            "keywords": [
+                "gd",
+                "image",
+                "imagick",
+                "laravel",
+                "thumbnail",
+                "watermark"
+            ],
+            "time": "2015-07-10 15:03:58"
+        },
         {
             "name": "jakub-onderka/php-console-color",
             "version": "0.1",
             ],
             "time": "2015-05-02 15:40:40"
         },
+        {
+            "name": "psr/http-message",
+            "version": "1.0",
+            "source": {
+                "type": "git",
+                "url": "https://github.com/php-fig/http-message.git",
+                "reference": "85d63699f0dbedb190bbd4b0d2b9dc707ea4c298"
+            },
+            "dist": {
+                "type": "zip",
+                "url": "https://api.github.com/repos/php-fig/http-message/zipball/85d63699f0dbedb190bbd4b0d2b9dc707ea4c298",
+                "reference": "85d63699f0dbedb190bbd4b0d2b9dc707ea4c298",
+                "shasum": ""
+            },
+            "require": {
+                "php": ">=5.3.0"
+            },
+            "type": "library",
+            "extra": {
+                "branch-alias": {
+                    "dev-master": "1.0.x-dev"
+                }
+            },
+            "autoload": {
+                "psr-4": {
+                    "Psr\\Http\\Message\\": "src/"
+                }
+            },
+            "notification-url": "https://packagist.org/downloads/",
+            "license": [
+                "MIT"
+            ],
+            "authors": [
+                {
+                    "name": "PHP-FIG",
+                    "homepage": "http://www.php-fig.org/"
+                }
+            ],
+            "description": "Common interface for HTTP messages",
+            "keywords": [
+                "http",
+                "http-message",
+                "psr",
+                "psr-7",
+                "request",
+                "response"
+            ],
+            "time": "2015-05-04 20:22:00"
+        },
         {
             "name": "psr/log",
             "version": "1.0.0",
index a7457bd1f90a8345a7aaaf6f7cd268ed24aac2a1..690d5fb96bb90c405aca3cebe9cf6168f9dc692f 100644 (file)
@@ -137,6 +137,11 @@ return [
         Illuminate\Validation\ValidationServiceProvider::class,
         Illuminate\View\ViewServiceProvider::class,
 
+        /**
+         * Third Party
+         */
+        Intervention\Image\ImageServiceProvider::class,
+
         /*
          * Application Service Providers...
          */
@@ -192,6 +197,12 @@ return [
         'Validator' => Illuminate\Support\Facades\Validator::class,
         'View'      => Illuminate\Support\Facades\View::class,
 
+        /**
+         * Third Party
+         */
+
+        'ImageTool' => Intervention\Image\Facades\Image::class,
+
     ],
 
 ];
diff --git a/database/migrations/2015_07_13_172121_create_images_table.php b/database/migrations/2015_07_13_172121_create_images_table.php
new file mode 100644 (file)
index 0000000..ecd074a
--- /dev/null
@@ -0,0 +1,32 @@
+<?php
+
+use Illuminate\Database\Schema\Blueprint;
+use Illuminate\Database\Migrations\Migration;
+
+class CreateImagesTable extends Migration
+{
+    /**
+     * Run the migrations.
+     *
+     * @return void
+     */
+    public function up()
+    {
+        Schema::create('images', function (Blueprint $table) {
+            $table->increments('id');
+            $table->string('name');
+            $table->string('url');
+            $table->timestamps();
+        });
+    }
+
+    /**
+     * Reverse the migrations.
+     *
+     * @return void
+     */
+    public function down()
+    {
+        Schema::drop('images');
+    }
+}
index 72f4f7b8e25332758a57a5da31b2c02eae6eb4f8..4cd440a11a745453c9f312882a7006e7f260dc9a 100644 (file)
@@ -3,13 +3,13 @@
 */
 
 h1 {
-  font-size: 5.625em;
+  font-size: 3.625em;
   line-height: 1.22222222em;
   margin-top: 0.48888889em;
   margin-bottom: 0.24444444em;
 }
 h2 {
-  font-size: 3.1875em;
+  font-size: 2.8275em;
   line-height: 1.294117647em;
   margin-top: 0.8627451em;
   margin-bottom: 0.43137255em;
index 021b43aaefca8d49e50af642da73719b5a2e7604..832d3f8ad8ca12c34b3b7403167ce303cc83ba04 100644 (file)
 
     <script>
         $(function() {
-            $('#html').editable({inlineMode: false});
+            $('#html').editable({
+                inlineMode: false,
+                imageUploadURL: '/upload/image',
+                imageUploadParams: {
+                    '_token': '{{ csrf_token() }}'
+                }
+            });
         });
     </script>
 @stop
\ No newline at end of file