Подтвердить что ты не робот

Лучший способ документировать параметры массива в PHPDoc?

Я изо всех сил пытаюсь написать удобочитаемую и простую для понимания документацию, которая описывает структуру с несколькими деревьями для параметров Array, которые передаются в функцию.

Вот пример структуры массива.

$arr = [
   'fields' => [
       'title' => [
           'name'     => 'Document.title',
           'format'   => 'string',
           'readonly' => true
       ]
   ]
];

Существует множество возможных вариантов для вышеуказанного массива, но он используется в качестве параметра функции, которая понимает эту структуру.

function doSomething(array $arr) { ... }

Я хотел бы задокументировать, как должен быть структурирован массив в PHPDoc, но я не уверен, каков правильный подход.

Вот что у меня сейчас.

/**
 * Holds configuration settings for each field in a model.
 * Defining the field options
 *
 * array['fields'] array Defines the feilds to be shown by scaffolding.
 * array['fields'][fieldName] array Defines the options for a field, or just enables the field if array is not applied.
 * array['fields'][fieldName]['name'] string Overrides the field name (default is the array key)
 * array['fields'][fieldName]['model'] string (optional) Overrides the model if the field is a belongsTo assoicated value.
 * array['fields'][fieldName]['width'] string Defines the width of the field for paginate views. Examples are "100px" or "auto"
 * array['fields'][fieldName]['align'] string Alignment types for paginate views (left, right, center)
 * array['fields'][fieldName]['format'] string Formatting options for paginate fields. Options include ('currency','nice','niceShort','timeAgoInWords' or a valid Date() format)
 * array['fields'][fieldName]['title'] string Changes the field name shown in views.
 * array['fields'][fieldName]['desc'] string The description shown in edit/create views.
 * array['fields'][fieldName]['readonly'] boolean True prevents users from changing the value in edit/create forms.
 * array['fields'][fieldName]['type'] string Defines the input type used by the Form helper (example 'password')
 * array['fields'][fieldName]['options'] array Defines a list of string options for drop down lists.
 * array['fields'][fieldName]['editor'] boolean If set to True will show a WYSIWYG editor for this field.
 * array['fields'][fieldName]['default'] string The default value for create forms.
 *
 * @param array $arr (See above)
 * @return Object A new editor object.
 **/

Моя проблема в том, что при создании HTML-документа он не очень хорошо отформатирован. Кроме того, я не уверен, что вышеизложенное четко объясняет структуру массива.

Есть ли альтернативный подход?

4b9b3361

Ответ 1

Просто добавление некоторых таблиц сделает его хорошо выглядящим и понятным

/**
 * Holds configuration settings for each field in a model.
 * Defining the field options
 *
 * array['fields']              array Defines the fields to be shown by scaffolding.
 *          [fieldName]         array Defines the options for a field, or just enables the field if array is not applied.
 *              ['name']        string Overrides the field name (default is the array key)
 *              ['model']       string (optional) Overrides the model if the field is a belongsTo associated value.
 *              ['width']       string Defines the width of the field for paginate views. Examples are "100px" or "auto"
 *              ['align']       string Alignment types for paginate views (left, right, center)
 *              ['format']      string Formatting options for paginate fields. Options include ('currency','nice','niceShort','timeAgoInWords' or a valid Date() format)
 *              ['title']       string Changes the field name shown in views.
 *              ['desc']        string The description shown in edit/create views.
 *              ['readonly']    boolean True prevents users from changing the value in edit/create forms.
 *              ['type']        string Defines the input type used by the Form helper (example 'password')
 *              ['options']     array Defines a list of string options for drop down lists.
 *              ['editor']      boolean If set to True will show a WYSIWYG editor for this field.
 *              ['default']     string The default value for create forms.
 *
 * @param array $arr (See above)
 * @return Object A new editor object.
 **/

Вложенный подход списка:

<ul>
    <li>
        array['fields'] array Defines the fields to be shown by scaffolding.
        <ul>
            <li>
                [fieldName]             array Defines the options for a field, or just enables the field if array is not applied.
                <ul>
                    <li> ['name']       <i><u>string</u></i> Overrides the field name (default is the array key) </li>
                    <li> ['model']      <i><u>string</u></i> (optional) Overrides the model if the field is a belongsTo associated value.</li>
                    <li> ['width']      <i><u>string</u></i> Defines the width of the field for paginate views. Examples are "100px" or "auto"</li>
                    <li> ['align']      <i><u>string</u></i> Alignment types for paginate views (left, right, center)</li>
                    <li> ['format']     <i><u>string</u></i> Formatting options for paginate fields. Options include ('currency','nice','niceShort','timeAgoInWords' or a valid Date() format)</li>
                    <li> ['title']      <i><u>string</u></i> Changes the field name shown in views.</li>
                    <li> ['desc']       <i><u>string</u></i> The description shown in edit/create views.</li>
                    <li> ['readonly']   <i><u>boolean</u></i> True prevents users from changing the value in edit/create forms.</li>
                    <li> ['type']       <i><u>string</u></i> Defines the input type used by the Form helper (example 'password')</li>
                    <li> ['options']    <i><u>array</u></i> Defines a list of string options for drop down lists.</li>
                    <li> ['editor']     <i><u>boolean</u></i> If set to True will show a WYSIWYG editor for this field.</li>
                    <li> ['default']    <i><u>string</u></i> The default value for create forms.</li>
                </ul>
            </li>
        </ul>
    </li>
 </ul>

Результат:

  •   
  •       array ['fields'] array Определяет поля, которые будут отображаться с помощью лесов.       
    •           
    •               [fieldName] array Определяет параметры для поля или просто включает поле, если массив не применяется.               
      •                   
      • ['name'] string Переопределяет имя поля (по умолчанию это массив)                  
      • ['model'] string (необязательно) Переопределяет модель, если это поле принадлежит связанному значению.                  
      • ['width'] string Определяет ширину поля для просмотра с разбивкой по страницам. Примеры: "100px" или "auto"                   
      • ['align'] string Типы выравнивания для просмотра страниц (слева, справа, в центре)                  
      • ['format'] string Параметры форматирования полей paginate. Параметры включают ( "валюта", "хороший", "хороший", "timeAgoInWords" или действительный формат Date()).                  
      • ['title'] string Изменяет имя поля, отображаемое в представлениях.                  
      • ['desc'] string Описание показано в окне редактирования/создания.                  
      • ['readonly'] boolean True запрещает пользователям изменять значение в файлах редактирования/создания.                  
      • ['type'] string Определяет тип ввода, используемый помощником формы (пример "пароль" )                  
      • ['options'] array Определяет список параметров строки для выпадающих списков.                  
      • ['editor'] boolean Если для параметра "Истина" будет отображаться редактор WYSIWYG для этого поля.                  
      • ['default'] string Значение по умолчанию для создания форм.
       

Если вы хотите, чтобы это выглядело фантазией, с небольшим количеством Css, он будет творить чудеса! XD

Ответ 2

Слишком поздно для вечеринки, но вот как я это делаю:

/**
 * Class constructor.
 *
 * @param array $params Array containing the necessary params.
 *    $params = [
 *      'hostname'     => (string) DB hostname. Required.
 *      'databaseName' => (string) DB name. Required.
 *      'username'     => (string) DB username. Required.
 *      'password'     => (string) DB password. Required.
 *      'port'         => (int) DB port. Default: 1433.
 *      'sublevel'     => [
 *          'key' => (\stdClass) Value description.
 *      ]
 *    ]
 */
 public function __construct(array $params){}

Подумайте, что это довольно чисто и легко понять, что $params должно быть.

Ответ 3

Я написал плагин для phpstorm, который позволяет указывать такие ключи:

(в основном просто более строгая версия формата @siannone)

/**
 * @param array $arr = [
 *     'fields' => [ // Defines the feilds to be shown by scaffolding
 *         $anyKey => [
 *             'name' => 'sale', // Overrides the field name (default is the array key)
 *             'model' => 'customer', // (optional) Overrides the model if the field is a belongsTo associated value.
 *             'width' => '100px', // Defines the width of the field for paginate views. Examples are "100px" or "auto"
 *             'align' => 'center', // Alignment types for paginate views (left, right, center)
 *             'format' => 'nice', // Formatting options for paginate fields. Options include ('currency','nice','niceShort','timeAgoInWords' or a valid Date() format)
 *             'title' => 'Sale', // Changes the field name shown in views.
 *             'desc' => 'A deal another person that results in money', // The description shown in edit/create views.
 *             'readonly' => false, // True prevents users from changing the value in edit/create forms.
 *             'type' => 'password', // Defines the input type used by the Form helper
 *             'options' => ['option1', 'option2'], // Defines a list of string options for drop down lists.
 *             'editor' => false, // If set to True will show a WYSIWYG editor for this field.
 *             'default' => '', // The default value for create forms.
 *         ],
 *     ],
 * ]
 */
public static function processForm($arr)
{
    $fieldName = 'sale';
    $arr['fields'][$fieldName][''];
}

enter image description here

Он также позволяет указывать клавиши @return:

/**
 * @return array [
 *     'success' => true,
 *     'formObject' => new Form,
 *     'errors' => [],
 * ]
 */
public static function processForm($arr);

enter image description here

Ответ 4

Можете ли вы использовать объекты вместо массивов? Это упростит документацию.

class Field {

    /**
     * The name of the thing.
     * @var string
     */
    protected $name;

    protected $model;
    protected $width;
    //...

    public function getName() {...}
    public function setName() {...}
    //...
}

class FieldList implements SomeKindOfIterator {

    /**
     * Some fields.
     * @var Field[]
     */
    protected $fields = array();

    /**
     * ...
     */
    public function push(Field $field) {
         $this->fields[] = $field;
    }

    //...
}

Затем вы можете использовать подсказку типа, где требуется класс.

/**
 * Do something.
 * @param FieldList $field_list The field.
 */
function doSomething(FieldList $field_list) {...}

Ответ 5

Синтаксис Markdown для объектной нотации (MSON) может быть лучшим выбором.

пример

/**
 * @param array $config
 *   + app (string, required) - app directory name
 *   + view (string, required) - view directory name
 *   + type (enum[string]) - site type
 *     + pc - PC version
 *     + wap - mobile version
 *     + other - other, default value
 *   + table_prefix (string) - database table prefix
 */

Ответ 6

Мне нравится это лучше:

 * @param array $doc
 *          'type'=>Doc::MY_DOC_TYPE,
 *          'created'=>$now,
 *          'modified'=>$now

Я просто вставляю код, откуда он инициализируется, быстро и легко.

Ответ 7

AS это чисто отображение, а не директива, и должно сохранять форматирование пространства внутри документов, я был бы склонен идти на удобочитаемость с отступом, а не с стенкой символов:

 * array['fields'] array Defines the feilds to be shown by scaffolding.
 *           [fieldName] array Defines the options for a field, or just enables
 *                             the field if array is not applied.
 *                 ['name'] string Overrides the field name (default is the
 *                                  array key)
 *                 ['model'] string (optional) Overrides the model if the field is
 *                                  a belongsTo assoicated value.
 *                 ['width'] string Defines the width of the field for paginate
 *                                  views.
 *                                  Examples are "100px" or "auto"
 *                 ['align'] string Alignment types for paginate views (left, 
 *                                 right, center)
 *                 ['format'] string Formatting options for paginate fields.
 *                                   Options include 'currency', 'nice',
 *                                  'niceShort', 'timeAgoInWords' or a valid 
 *                                  Date() format)
 *                 ['title'] string Changes the field name shown in views.
 *                 ['desc'] string The description shown in edit/create views.
 *                 ['readonly'] boolean True prevents users from changing the
 *                                 value in edit/create forms.
 *                 ['type'] string Defines the input type used by the Form helper
 *                                  (example 'password')
 *                 ['options'] array Defines a list of string options for drop-
 *                                  down lists.
 *                 ['editor'] boolean If set to True will show a WYSIWYG editor
 *                                  for this field.
 *                 ['default'] string The default value for create forms.

Хотя использование реального определения массива PHP с отступом еще более чистое

Ответ 8

Массивы в PHP больше похожи на анонимные структуры.

Для произвольных структур данных существует ряд валидаторов схем, но, к сожалению, они не получили широкого распространения в подсказках типов. Возможно, некоторые распространенные схемы имеют плагины? Проблема в том, что вещи работают только в одном или нескольких местах. Вы могли бы получить правильную вещь, работающую для вашей IDE, но запустить статический анализ, и все это может попасть в ад.

Необходимо позаботиться о том, чтобы отделить вещи, чтобы, если это возможно, другие инструменты, не поддерживающие схему, например, через плагин, просто игнорировали ее.

PHPDoc, как правило, поддерживается везде, но также очень ограничен.

Часто есть предложения, но нет действительно хорошего стандарта. Большинство решений являются нестандартными, не широко поддерживаемыми, частичными взломами с ограничениями или чисто поверхностными (документация).

Существуют конкретные реализации в определенных местах, но нет ничего распространенного и посвященного самому PHP. Хотя вы можете создавать свои собственные схемы в PHP IDE, как правило, не хватает приличных мостов кода, даже тех, у которых в названии PHP.

Вы должны определить свою структуру поля отдельно. Ваша внешняя структура данных в виде псевдокода @key fields field[], а не в виде многомерных массивов. Концептуально и запутанно вы можете пойти так далеко:

@start struct custom
@key \stdClass *
@end struct

@start struct fields
@key string hostname
@key string databaseName
@key string password
@key int port=1433
@key custom|undefined sublevel
@end struct

@start struct connection
@key fields fields
@end struct

Или украсть у C, а затем изобрести язык...

struct connection {
    struct fields {
        string hostname;
        string databaseName;
        string password;
        int port = 1433;
        custom optional sublevel {
            stdClass *;
        };
    };
};

Вы можете придумать схему, основанную на структурах, чтобы разрешить как плоскую, так и вложенную. Вкладка должна быть по умолчанию, вещи должны быть определены так, чтобы быть настолько доступными, насколько это необходимо для повторного использования.

Необычный подход состоит в том, чтобы вместо этого использовать объекты. Это не обязательно связано с использованием таких интерфейсов, как доступ к массиву. В PHP объект оборачивает массив для свойств. Можно привести массив к объекту (без реализации, только свойства) и обратно.

Если вместо этого вы используете объекты в качестве ассоциативного массива ($ array [$ key] против $object-> {$ key}), то вы можете создать фиктивные объекты, чтобы по крайней мере обмануть IDE...

final class PersonStruct {
    /** @var int */
    public $x;

    /** @var int $y */

    public int $z;
}

Из этих трех опций, которые могут работать или не работать, зависит от используемого инструмента.

Тогда ты можешь лгать...

/** @var PersonStruct $ps */
$ps = (object)['x' => 0, 'y' => 1, 'z' => 2];

/**
 * @param PersonStruct $ps
 * @return PersonStruct
 */
function f(object $ps):object {
    return $ps;
}

/**
 * @param PersonStruct $ps
 * @return PersonStruct
 */
function f(stdClass $ps):stdClass {
    return $ps;
}

Проблема в том, что это означает преобразование массивов в объекты. Это влияет как на производительность, так и на изменения, передаваемые по значению для передачи по ссылке. Что быстрее спорно. Массивы должны быть теоретически более быстрыми, хотя объекты имеют преимущества, являющиеся ссылками по умолчанию, и лучше работают с JSON, который отличает объект от массива в отличие от PHP.

Объекты также не поддерживают свойство, которое может быть не очень хорошо настроено в отношении хинтинга типов, даже если свойства объекта являются просто массивом PHP (используйте ->{key} вместо [key]). Есть потенциал для других странных вещей.

Если производительность действительно важна, вы можете превратить PHP в скомпилированный язык. Таким же образом, вы можете расширить интерфейс, чтобы сделать объект компилируемым, вы можете сделать то же самое, где вы можете делать все с ООП и автозаполнением, но затем можете сделать эквивалентное встраивание класса, указав свойство, которое он переносит, затем используя Отражение в значительной степени заменяет использование содержимым методов сопоставления с несколькими необходимыми дополнительными битами (отмечая, что нужно встроить или преобразовать в процедурное, одно свойство для переноса или несколько и т.д.).

Концепция похожа на бокс и распаковку. Если вы действительно помешаны на поддержке SA и широкой поддержке IDE (автозаполнение, проверка и т.д.), Анализаторов, инструментов и т.д., То это может быть единственным способом.