Giter Site home page Giter Site logo

laravel-reportable's Introduction

Laravel Reportable

Build Status PHP from Packagist Latest Version License

Installation

Require this package, with Composer, in the root directory of your project.

$ composer require artisanry/reportable

To get started, you'll need to publish the vendor assets and migrate:

php artisan vendor:publish --provider="Artisanry\Reportable\ReportableServiceProvider" && php artisan migrate

Usage

Setup a Model

<?php

namespace App;

use Artisanry\Reportable\HasReports;
use Illuminate\Database\Eloquent\Model;

class Post extends Model
{
    use HasReports;
}

Examples

The User Model reports the Post Model

$post->report([
    'reason' => \Str::random(10),
    'meta' => ['some more optional data, can be notes or something'],
], $user);

Create a conclusion for a Report and add the User Model as "judge" (useful to later see who or what came to this conclusion)

$report->conclude([
    'conclusion' => 'Your report was valid. Thanks! We\'ve taken action and removed the entry.',
    'action_taken' => 'Record has been deleted.', // This is optional but can be useful to see what happend to the record
    'meta' => ['some more optional data, can be notes or something'],
], $user);

Get the conclusion for the Report Model

$report->conclusion;

Get the judge for the Report Model (only available if there is a conclusion)

$report->judge(); // Just a shortcut for $report->conclusion->judge

Get an array with all Judges that have ever "judged" something

Report::allJudges();

Get unjudged reports (those without conclusions)

Report::unjudged(); // returns query builder.

Changing the user reporter model

Set your user model in the config('auth.providers.users.model');

Testing

$ phpunit

Security

If you discover a security vulnerability within this package, please send an e-mail to [email protected]. All security vulnerabilities will be promptly addressed.

Credits

This project exists thanks to all the people who contribute.

License

Mozilla Public License Version 2.0 (MPL-2.0).

laravel-reportable's People

Contributors

dependabot-preview[bot] avatar faustbrian avatar livijn avatar marky291 avatar renovate[bot] avatar

Stargazers

 avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar  avatar

Watchers

 avatar

laravel-reportable's Issues

[Feature Request?]: Custom Report Model

Hi,

I don't know if it exists yet, but Is there any way we can add a custom report model that extends the original report model? This would be convenient to add anything extra we need (such as adding Searchable trait etc to go to elasticsearch, etc).

Thanks!

question: reporting a User

Hello!

What do i do, when i want to report another User related model?

Something like shown below. I made it, with a workaround today and probably encountered another possible bug (See comments in trait InteractsWithReports).

I hope the code below is clean enough to understand what i am going to do.

Basically it's a POST REST call to a route like 'https://my-cool-api/reports/users/1'

Thanks in advance!

routes.php

Route::namespace('Reports')->prefix('reports')->group(function ($router) {
    $router->post('/{type}/{id}', 'ReportsController@report');
});

ReportStoreRequest.php

class ReportStoreRequest extends BaseRequest
{
    public function rules()
    {
        return [
            'id' => ['required', new HasReported($this->type)],
            'type' => 'required|in:users',
        ];
    }

    public function attributes()
    {
        return [
            'type' => trans('reports.attributes.type'),
        ];
    }

    protected function validationData()
    {
        return array_merge($this->request->all(), [
            'id' => $this->route()->parameter('id'),
            'type' => $this->route()->parameter('type'),
        ]);
    }
}

ReportsController.php

class ReportsController extends Controller
{
    public function report(ReportStoreRequest $request)
    {
        $this
            ->repository($request->type)
            ->findOrFail($request->id)
            ->report([
                'reason' => trans('reports.verbs.reported'),
                'reportable_id' => $request->id, # part of my: a user can report a user workaround
            ], auth()->user());

        return api_response()->accepted();
    }

    private function repository(string $type): RepositoryContract
    {
        return Str::plural($type)(); // resolves users() from helpers.php
    }
}

helpers.php

if (! function_exists('users')) {
    function users()
    {
        return app(App\Contracts\UserRepositoryContract::class);
    }
}

App\Models\User.php

class User extends Authenticatable implements ...
{
    use InteractsWithReports;
}

TraitMagic

trait InteractsWithReports
{
    use BrianFaust\Reportable\Traits\HasReports;

    public function reports(): MorphMany
    {
        // fixes wrong name: reportable (when using reportable, auth()->user()->reports remain empty)
        return $this->morphMany(Report::class, 'reporter');
    }

    public function hasReported(string $model, string $reportableId): bool
    {
        return $this
            ->reports
            ->where('reportable_type', '=', $model)
            ->where('reportable_id', '=', $reportableId)
            ->where('reporter_id', '=', $this->id)
            ->isNotEmpty();
    }

    /**
     * Intentionally overwritten to provide the feature that a User is able to report another User.
     */
    public function report($data, Model $reporter): Report
    {
        $report = (new Report())->fill(array_merge($data, [
            'reporter_id' => $reporter->id,
            'reporter_type' => get_class($reporter),
        ]));

        $report->reportable_type = $report->reportable_type ?: get_class($this);
        $report->reportable_id = $report->reportable_id ?: $data['reportable_id']; // forgot Arr::get($data, '...');
        $report->reporter_id = $report->reporter_id ?: auth()->user()->id;

        $this->reports()->save($report);

        // The update below fixes reporter_id not properly being set.
        // When reporting App\Models\User, reporter_id gets value of reportable_id.
        $report->update([
            'reporter_id' => auth()->user()->id,
        ]);

        return $report;
    }
}

CustomRule

class HasReported implements Rule
{
    private $model;

    public function __construct(string $type)
    {
        $model = ucfirst(Str::singular($type));

        $this->model = "App\\Models\\{$model}";
    }

    public function passes($attribute, $value)
    {
        return ! auth()->user()->hasReported($this->model, $value);
    }

    public function message()
    {
        return trans('reports.messages.has_reported');
    }
}

Invalid instance passed

Argument 1 passed to Artisanry\Reportable\Models\Report::scopeUnjudged() must be an instance of Artisanry\Reportable\Models\Builder, instance of Illuminate\Database\Eloquent\Builder given.

Namespacing broken on namechange

I believe namespacing has become incorrect for your package and now no longer works.
"namespace BrianFaust\Reportable" but package is now "namespace artisanry/reportable"

Also broke my extension class. (usage import of ur package cannot be found)
Screenshot 2019-06-06 at 19 22 28

Could you update to 2.2 to be the same with Master?

Problem with:

our requirements could not be resolved to an installable set of packages.

  Problem 1
    - Installation request for faustbrian/laravel-reportable ^2.1 -> satisfiable by faustbrian/laravel-reportable[2.1.0].
    - Conclusion: remove laravel/framework v5.6.33
    - Conclusion: don't install laravel/framework v5.6.33

Feature Requests

Nice to have:

  • List all reported models
  • List reported models filtered by * (concluded Only, Unconcluded, etc)
  • Remove All reports from Model
  • Remove unconcluded reports from Model
  • Added multiple status for report ("unconcluded", "in review", "denied" etc )

Recommend Projects

  • React photo React

    A declarative, efficient, and flexible JavaScript library for building user interfaces.

  • Vue.js photo Vue.js

    ๐Ÿ–– Vue.js is a progressive, incrementally-adoptable JavaScript framework for building UI on the web.

  • Typescript photo Typescript

    TypeScript is a superset of JavaScript that compiles to clean JavaScript output.

  • TensorFlow photo TensorFlow

    An Open Source Machine Learning Framework for Everyone

  • Django photo Django

    The Web framework for perfectionists with deadlines.

  • D3 photo D3

    Bring data to life with SVG, Canvas and HTML. ๐Ÿ“Š๐Ÿ“ˆ๐ŸŽ‰

Recommend Topics

  • javascript

    JavaScript (JS) is a lightweight interpreted programming language with first-class functions.

  • web

    Some thing interesting about web. New door for the world.

  • server

    A server is a program made to process requests and deliver data to clients.

  • Machine learning

    Machine learning is a way of modeling and interpreting data that allows a piece of software to respond intelligently.

  • Game

    Some thing interesting about game, make everyone happy.

Recommend Org

  • Facebook photo Facebook

    We are working to build community through open source technology. NB: members must have two-factor auth.

  • Microsoft photo Microsoft

    Open source projects and samples from Microsoft.

  • Google photo Google

    Google โค๏ธ Open Source for everyone.

  • D3 photo D3

    Data-Driven Documents codes.