1
votes

I have a page model and a textblock model for creating pages with as many textblocks as needed. I'm using sortable from jquery ui to sorter the textblocks by position field in migration table. So every time I'm creating a textblock the position will count + 1, starting from 1.

Now I'm setting up 2 faker factories, 1 for pages and 1 for generating dummy textblocks on the pages. I'm wondering how I can count the amount of random textblocks the factory will create? So I can say every time the page factory creates a page with a few textblocks the counter won't override the amount of textblocks each page has.

 $factory->define(Textblock::class, function (Faker $faker) {

return [
    'page_id' => Page::all()->random()->id,
    'title' => $faker->sentence(rand(2, 5)),
    'summary' => $faker->text,
    'position' => // how can i code this ?
    'visible' => $faker->boolean($chanceOfGettingTrue = 50),

]; });
1

1 Answers

0
votes

You could create a Counter object to keep all the incrementations in memory. Something similar to:

class Counter
{
    private static $counters = [];

    public static function nextCounterFor($key, $default = 0)
    {
        if (!isset(self::$counters[$key])) {
            if (is_callable($default)) {
                 $default = $default();
            }
            if (!is_int($default)) {
                 throw new \RuntimeException('The default value must be an integer');
            }
            self::$counters[$key] = $default;
        }

        return ++self::$counters[$key];
    }
}

Then you can use it to generate new positions for the given page ID. If there is no key defined yet, you must take the last position used for that page from the db (if it exists)

$factory->define(Textblock::class, function (Faker $faker) {

  $page = Page::inRandomOrder()->first();
 
  $position = Counter::nextCounterFor($page->id, static function() use ($page) {
       $lastPosition = Textblock::where('page_id', $page->id)->orderBy('position', 'DESC')->first();
       return $lastPosition !== null ? $lastPosition->position : 0;
  });

  return [
    'page_id' => $page->id,
    'title' => $faker->sentence(rand(2, 5)),
    'summary' => $faker->text,
    'position' => $position,
    'visible' => $faker->boolean($chanceOfGettingTrue = 50),
  ];
});