Skip to content

Commit

Permalink
Implement the new spec for inventory schema (#15)
Browse files Browse the repository at this point in the history
* First pass at the new Compartment schema

* Remove unused imports

* Add a first pass at the new subcompartment

* FIrst pass at the new Inventory schema

* FIrst pass at the stratum spec

Introduces compulsory params in the constructor

* Remove old spec

* Better packaging and typing of enums. Compulsory properties for Geojson schema classes.

* Comment on lower case geojson enum values

* Compulsory properties for Compartment, and phpstan fixes

* Fix ListingTest

* Fix typoe in exception message

* Compulsory properties for the subcompartment

* Compulsory properties for inventory schema

* Small doc tweaks
  • Loading branch information
sfreytag authored Oct 10, 2024
1 parent 9e937a6 commit 5f646dc
Show file tree
Hide file tree
Showing 22 changed files with 708 additions and 439 deletions.
12 changes: 12 additions & 0 deletions src/Dto/Enum/ListingStateEnum.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
<?php

declare(strict_types=1);

namespace CloudForest\ApiClientPhp\Dto\Enum;

enum ListingStateEnum: string
{
case DRAFT = 'DRAFT';
case OPEN = 'OPEN';
case CLOSED = 'CLOSED';
}
11 changes: 11 additions & 0 deletions src/Dto/Enum/ListingWhenEnum.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
<?php

declare(strict_types=1);

namespace CloudForest\ApiClientPhp\Dto\Enum;

enum ListingWhenEnum: string
{
case NOW = 'NOW';
case FUTURE = 'FUTURE';
}
12 changes: 12 additions & 0 deletions src/Dto/Enum/PriceTypeEnum.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
<?php

declare(strict_types=1);

namespace CloudForest\ApiClientPhp\Dto\Enum;

enum PriceTypeEnum: string
{
case NONE = 'NONE';
case OFFERS = 'OFFERS';
case EXACT = 'EXACT';
}
41 changes: 12 additions & 29 deletions src/Dto/ListingDto.php
Original file line number Diff line number Diff line change
Expand Up @@ -4,32 +4,15 @@

namespace CloudForest\ApiClientPhp\Dto;

use CloudForest\ApiClientPhp\Schema\StandardCompartment;

enum ListingState: string
{
case DRAFT = 'DRAFT';
case OPEN = 'OPEN';
case CLOSED = 'CLOSED';
}

enum PriceType: string
{
case NONE = 'NONE';
case OFFERS = 'OFFERS';
case EXACT = 'EXACT';
}

enum ListingWhen: string
{
case NOW = 'NOW';
case FUTURE = 'FUTURE';
}
use CloudForest\ApiClientPhp\Schema\CompartmentSchema;
use CloudForest\ApiClientPhp\Dto\Enum\ListingStateEnum;
use CloudForest\ApiClientPhp\Dto\Enum\PriceTypeEnum;
use CloudForest\ApiClientPhp\Dto\Enum\ListingWhenEnum;

/**
* ListingDto defines the shape of the listing data used by the CloudForest API.
*
* @package CloudForest
* @package CloudForest\Dto
*/
class ListingDto
{
Expand All @@ -49,9 +32,9 @@ class ListingDto
* Currently DRAFT listings are not fully supported so only create listings
* in an OPEN state.
*
* @var value-of<ListingState>
* @var ListingStateEnum
*/
public $state = 'OPEN';
public $state = ListingStateEnum::OPEN;

/**
* The title of the listing.
Expand All @@ -71,17 +54,17 @@ class ListingDto
* The price type. Set it to NONE until the user has a chance to go to
* CloudForest to enter their preferred pricing.
*
* @var value-of<PriceType>
* @var PriceTypeEnum
*/
public $priceType = 'NONE';
public $priceType = PriceTypeEnum::NONE;

/**
* When the listing is available. Set it to NOW until the user has a chance
* to go to CloudForest to enter their preferred availability.
*
* @var value-of<ListingWhen>
* @var ListingWhenEnum
*/
public $when = 'NOW';
public $when = ListingWhenEnum::NOW;

/**
* The units in which the listing is available as a freeform string. EG
Expand Down Expand Up @@ -143,7 +126,7 @@ class ListingDto
* For Standing Timber this is likely to be the StandardCompartment
* specification supplied as a list. For other categories alternative data
* structures can be used.
* @var array<StandardCompartment>
* @var array<CompartmentSchema>
*/
public $inventory = [];

Expand Down
94 changes: 94 additions & 0 deletions src/Schema/CompartmentSchema.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,94 @@
<?php

declare(strict_types=1);

namespace CloudForest\ApiClientPhp\Schema;

use CloudForest\ApiClientPhp\Schema\GeojsonSchema;
use CloudForest\ApiClientPhp\Schema\SubcompartmentSchema;
use CloudForest\ApiClientPhp\Schema\Enum\CompartmentTypeEnum;
use CloudForest\ApiClientPhp\Schema\Enum\GeojsonGeometryTypeEnum;

/**
* CompartmentSchema defines the shape of the compartment data used to send an
* inventory to the CloudForest API.
*
* @package CloudForest\Schema
*/
class CompartmentSchema
{
/**
* The ID of the compartment. If known, it is a UUID string, else null.
*
* @var string|null
*/
public $id = null;

/**
* The type of the compartment. This allows the logic unit 'compartment' to
* also represent other physical units like parcels and zones, if necessary.
*
* @var CompartmentTypeEnum
*/
public $type = CompartmentTypeEnum::COMPARTMENT;

/**
* The name of the compartment, or null if not known.
*
* @var string|null
*/
public $name = null;

/**
* The number of the compartment. This is a string representation of an
* integer and cannot be null.
*
* @var string
*/
public $number;

/**
* Any notes about the compartment, or null if none.
*
* @var string|null
*/
public $notes = null;

/**
* The boundary of the compartment as a Geojson polygon.
*
* @var GeojsonSchema
*/
public $boundary;

/**
* The centroid of the compartment as a Geojson point.
*
* @var GeojsonSchema
*/
public $centroid;

/**
* The collection of Subcompartments within this Compartment.
*
* @var Array<SubcompartmentSchema>
*/
public $subcompartments = [];

/**
* Constructor. Supply the required properties (those without defaults).
* @param string $number
* @return void
* @throws \Exception
*/
public function __construct(string $number)
{
if (mb_strlen($number) < 1) {
throw new \Exception('Compartment number cannot be less than 1 character');
}

$this->number = $number;
$this->boundary = new GeojsonSchema(GeojsonGeometryTypeEnum::POLYGON);
$this->centroid = new GeojsonSchema(GeojsonGeometryTypeEnum::POINT);
}
}
13 changes: 13 additions & 0 deletions src/Schema/Enum/CompartmentTypeEnum.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
<?php

declare(strict_types=1);

namespace CloudForest\ApiClientPhp\Schema\Enum;

enum CompartmentTypeEnum: string
{
case COMPARTMENT = 'COMPARTMENT';
case PARCEL = 'PARCEL';
case ZONE = 'ZONE';
case OTHER = 'OTHER';
}
12 changes: 12 additions & 0 deletions src/Schema/Enum/GeojsonGeometryTypeEnum.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,12 @@
<?php

declare(strict_types=1);

namespace CloudForest\ApiClientPhp\Schema\Enum;

enum GeojsonGeometryTypeEnum: string
{
// Lower case values to match GeoJSON spec
case POLYGON = 'Polygon';
case POINT = 'Point';
}
11 changes: 11 additions & 0 deletions src/Schema/Enum/GeojsonTypeEnum.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,11 @@
<?php

declare(strict_types=1);

namespace CloudForest\ApiClientPhp\Schema\Enum;

enum GeojsonTypeEnum: string
{
// Lower case value to match GeoJSON spec
case FEATURE = 'Feature';
}
13 changes: 13 additions & 0 deletions src/Schema/Enum/SubcompartmentTypeEnum.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,13 @@
<?php

declare(strict_types=1);

namespace CloudForest\ApiClientPhp\Schema\Enum;

enum SubcompartmentTypeEnum: string
{
case SUBCOMPARTMENT = 'SUBCOMPARTMENT';
case STAND = 'STAND';
case SUBZONE = 'SUBZONE';
case OTHER = 'OTHER';
}
39 changes: 39 additions & 0 deletions src/Schema/GeojsonGeometrySchema.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,39 @@
<?php

declare(strict_types=1);

namespace CloudForest\ApiClientPhp\Schema;

use CloudForest\ApiClientPhp\Schema\Enum\GeojsonGeometryTypeEnum;

/**
* GeojsonGeometrySchema defines a geometry for use with GeojsonSchema.
*
* @package CloudForest\Schema
*/
class GeojsonGeometrySchema
{
/**
* The geometry type. We only send Points and Polygons to CloudForest.
*
* @var GeojsonGeometryTypeEnum
*/
public $type;

/**
* The coordinates, as an array of [Longitude, Latitude] tuples.
*
* @var array<array{float,float}>
*/
public $coordinates = [];

/**
* Constructor. Supply the required properties (those without defaults).
* @param GeojsonGeometryTypeEnum $type
* @return void
*/
public function __construct(GeojsonGeometryTypeEnum $type)
{
$this->type = $type;
}
}
43 changes: 43 additions & 0 deletions src/Schema/GeojsonSchema.php
Original file line number Diff line number Diff line change
@@ -0,0 +1,43 @@
<?php

declare(strict_types=1);

namespace CloudForest\ApiClientPhp\Schema;

use CloudForest\ApiClientPhp\Schema\GeojsonGeometrySchema;
use CloudForest\ApiClientPhp\Schema\Enum\GeojsonTypeEnum;
use CloudForest\ApiClientPhp\Schema\Enum\GeojsonGeometryTypeEnum;

/**
* GeojsonSchema defines the shape of a Geojson geographic data structure to
* send to the CloudForest API.
*
* @package CloudForest\Schema
*/
class GeojsonSchema
{
/**
* The Geojson type. We only send Features types to CloudForest, not
* FeatureCollection types, so this is hardcoded to 'Feature'.
*
* @var GeojsonTypeEnum
*/
public $type = GeojsonTypeEnum::FEATURE;

/**
* The Geojson geometry.
*
* @var GeojsonGeometrySchema
*/
public $geometry;

/**
* Constructor. Supply the required properties (those without defaults).
* @param GeojsonGeometryTypeEnum $geometryType
* @return void
*/
public function __construct(GeojsonGeometryTypeEnum $geometryType)
{
$this->geometry = new GeojsonGeometrySchema($geometryType);
}
}
Loading

0 comments on commit 5f646dc

Please sign in to comment.