Скачивание и установка

Вы можете посмотреть видео-урок или прочитать инструкции ниже.

Зависимости

Скачайте и установите:

  1. NodeJs - с оффициального сайта
  2. MariaDB - с оффициального сайта
  3. Git - с оффициального сайта
  4. Navicat - с оффициального сайта
    Или любую другую программу для управления базами данных MariaDB

Скачивание

  Скачать GoCore
  1. Откройте проект в вашей среде разработки.
  2. Установите node modules, выполнив команду "npm i" через терминал. (Если вы только что установили nodeJs, терминал может не знать команду npm, нужно перезагрузить компьютер)

Подключение и настройка БД

  1. Откройте navicat или другую программу для управления базами данных.
  2. Создайте новое подключение к MariaDB.

    Connection name: localhost

    User name: root

    Password: Пароль, который вы указали при установке mariaDB

  3. В созданном подключении создайте новую базу данных.

    Database name: Придумайте название вашей базы данных, оно же должно быть прописано в конфиге GoCore (config/config.json), в mysqlConnection - database

    Character set: utf8

    Collation: utf8_general_ci

  4. Залить дамп в созданную базу (execute sql file), сам дамп лежит в GoCore, в папке DB, файл .sql

Настройка среды и запуск

Вы можете использовать вашу любимую среду разработки, мы пользуемся PhpStorm/WebStorm и другими продуктами JetBrains.

  1. Откройте проект в вашей среде разработки.
  2. Зайдите в /config/config_example.json и создайте его копию, назовите config.json
  3. В созданном файле config.json укажите:

    Название базы данных (mysqlConnection -> database) : Название вашей базы данных

    Пароль к базе данных (mysqlConnection -> password) : Пароль от вашей базы данных

  4. Настройте конфигурацию запуска проекта:

    Создайте новый конфиг для NodeJs.

    Название: DEV

    NodeJs interpreter: Укажите путь к nodejs.exe

    В качестве запускаемого javascript file укажите путь к файлу: /bin/www.js

    Application parameter: config.json

    Сохраните конфигурацию.

  5. Запустите проект.
  6. Зайдите на localhost:8080 и авторизуйтесь в системе

    Логин: admin@go-core.ru

    Пароль: welcomebro

Обзор интерфейса

Хедер

В хереде расположены:
  1. Логотип, вы можете заменить его на логотип вашего проекта.
  2. Блок пользователя, по клику открывает форму пользователя, в которой можно редактировать данные и заменить пароль.
  3. Выход, выходит из системы, если нажать с CTRL - выведет окно смены пароля.

Меню

Меню системы, содержит базовые элементы и настривается через Settings / Menu editor

Базовые разделы:

  1. Dashboard

    Рабочий стол: Здесь обычно рамполагаются ключевые разделы системы.

  2. Basic data

    Базовые данные: Они же справочники, сюда обычно размещают вспомогательные таблицы системы.

  3. Site

    Раздел для управления сайтом: Здесь могут быть разделы сайта подключенного к GoCore или любые другие данные, которые вы будете отдавать по внешнему API или в связке с версией GoCore для сайта/приложения.

  4. Reports

    Отчеты: Сюда стоит размещать вызов генератора различных отчетов.

  5. Settings

    Editor types: Типы редакторов полей в системе, здесь размещена таблица существующих редакторов. Для создания новых типов редакторов необходимо создать запись "типа редактора" и написать код в файлах tableNew.js, classicTable.js, FormNew.js в правильных местах, о чем будет написано ниже в документации.

    Classes: Базовые классы системы а также те классы, которые будете создавать вы.

    Class fields: Все колонки всех классов в системе.

    Client objects: Клиентские объекты, сущности наследуемые от классов, например таблицы, формы или фреймы. Здесь расположены все базовые клиентские объекты системы а также те клиентские объекты которые создадите вы.

    Menu editor: Редактор меню, здесь происходит управление меню.

    Filter types: Типы фильтров для таблиц, здесь расположена таблица существующих фильтров. Для создания новых фильтров необходимо создать запись "типа меню" и написать код в файлах tableNew.js и classicTable.js, в правильных местах, о чем будет написано ниже в документации.

  6. Access

    Отказы доступа: Таблица - лог отказов доступа со всей необходимой информацией и удобными функциями выдачи доступа.

    Companies: Базования таблица компаний, использвуется для различного рода внешних авторизаций. ВАНЯ

    Users: Базования таблица пользователей, здесь администратор может управлять пользователями, назначать им роли и доступы.

    Roles: Базования таблица ролей, здесь администратор может управлять ролями и их доступом.

    Операции класса: Таблица со всеми операциями всех классов. ВАНЯ

    Доступ к операциям: Таблица со всеми доступами ко всем операциям всех классов. ВАНЯ

    User types: Типы пользователя для различных типов авторизаций, обычный пользватель, роль, администратор, внешний сайт или приложение и т.д.

    User statuses: Справочник статусов пользователей, активный, заблокированный, ожидает подтверждения.

    Список доступа: ВАНЯ.

  7. Temporary

    Временный раздел: Вспомогательный раздел меню, куда автоматически выводятся таблицы всех созданных вами классов.

  8. System

    Системные настройки: ВАНЯ.

  9. Dynamic fields

    Динамические поля: ВАНЯ.

Контент

GoCore предполагает разработку сингл-пейдж приложений, в основную контентуню область подгружаются таблицы, фреймы или любые другие интерфейсы.

Таблицы

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

Кастомный функционал таблиц удобно писать за счет стандатизации js файлов и качественно организованного доступа к данным.

  1. Заголовок таблицы: подтягивается из профайла класса или клиентского объекта.

  2. Кнопки

    Create: Создает новую запись в таблице, которую можно заполнить и сохранить.

    Create in form: Открывет форму создания сущности в модальном окне, которую можно сверстать на ваше усмотрение.

    Delete: Удаляет выбранные строки.

    Кастомные кнопки: Вы можете скрывть и добавлять кнопки в этот блок.

  3. Фильтры

    Фильтры гибко настраиваются в профайле класса или клиентского объекта

  4. Кнокпи применить / сбросить фильтры.
  5. Пагинация

    * Для огромных таблиц, в целях оптимизации скорости и нагрузки на БД, в платформе предусмотрена система порционной загрузки итогового количества страниц, настривается галочкой.

  6. Количество записей на странице.

    Количество по умолчанию настраивается в профайле класса или клиентского объекта.

  7. Быстрый поиск.

    В профайле таблицы можно настроить колонки по которым будет осуществляться быстрый поиск.

  8. Функции таблицы:

    Save: Кнопка сохранения, сохраняет измененные данные и созданные строки, имеет множество конфигураций, например, можно попросить пользователя подтвердить действие перед сохранением.

    Filters: Открывает / закрывает панель с фильтрами.

    Сброс фильтров: Сбрасывает все фильтры, в том числе быстрый поиск.

    Настройка видимости колонок: Пользователь может настроить видимость колонок под себя, настройки сохранятся в localStorage, туда же сохраняются ширины колонок которые изменял пользователь.

    Открыть доп. функции: Кнопка с иконкой в виде 2-х документов открывает и закрывает нижнюю панель дополнительных функций.

    Refresh: Обновляет таблицу.

  9. Дополниетльные функции таблицы:

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

    Export to excel: Выгрузка данных таблицы в эксель с настройкой количества и кнопкой выгрузить всё.

    Configure access: Настройка доступов к данным. ВАНЯ.

  10. Новая строка в таблице.

    Создавать и заполнять можно одну или несколько строк, после - сохранить изменения.

  11. Контекстное меню.

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

    Open in form: Открыть в форме, кнопка которая есть по умолчанию для тех таблиц, у которых в профайле указана соответствующая форма.

    Кастомные кнопки: Вы можете создавать кастомные функции для работы с данными таблицы, прописывать их состояние и видимость используя удобные настройки в коде.

  12. Редакторы полей.

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

Формы

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

Формы легко и быстро верстать за счет простого встроенного шаблонизатора.

Кастомный функционал форм удобно писать за счет стандатизации js файлов и качественно организованного доступа к данным.

  1. Заголовок формы: подтягивается из профайла класса или клиентского объекта.

  2. Табы: В верстке формы можно удобно заложить табы.

  3. Save: Сохраняет изменения в форме, работает по CTRL+S.

  4. Управление окном.

    Refresh: Перезагружает форму.

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

    Уменьшить / увеличить окно: Переключает окно из полноэкранного режима и обратно.

    Закрыть: Закрывает форму.

  5. Хедлайн формы.

    Это заголовок формы, в отличии от заголовка в верхней панели, этот заголовок уже выведен в верстке на базе удобного втроенного шаблонизатора, чтобы вывести только значение колонки необходимо написать {+{column_name}+}

  6. Поля формы.

    Поля формы выводятся исходя из данных, профайла и верстки. Чтобы вывести поле с редактором, которое будет знать откуда брать данные, как их визуализировать и куда сохранять необходимо написать {{{column_name}}}

    Помимо полей, в форму можно выводить любые сущности, таблицы, фреймы, кастомный функционал, плагины и пр.

  7. Кастомные кнопки.

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

  8. Свернутые формы

    Бар, где размещаются все открытые формы, как в виндоус.

Обзор директорий - фронтэнд

Assets - стили, шрифты, скрипты, плагины, изображения.



/public/assets/..

  1. Стили:

    99% стилей платформы описаны в файлах ..css/components.css и ../css/swag_styles/components.css, если вы хотите дополнить стили касающиеся базовых элементов платформы, пишите их в ../css/swag_styles/components.css

    Для написания стилей которые относятся конкретно к вашему проекту, пишите их в файл project_styles.css

  2. Шрифты:

    Лежат в ../fonts

  3. Скрипты:

    Лежат в директори ../js. Их много, подробнее о важных скриптах и о том где писать скрипты для вашего проекта будет написано ниже в документации.

  4. Плагины:

    Лежат в ../plugins. Вы можете подключать любые плагины на свое усмотрение в index.html размещая их в этой директории.

  5. Изображения:

    Лежат в ../img. Размещайте ваши картинки в этой директории, при необходимости создавайте осмысленные поддиректории.

Html - Таблицы, формы, фреймы.

/public/html/..

  1. Таблицы ../tables/require

    По умолчанию таблицы работают без дополнительных скриптов, однако, если вам нужно сделать контекстное меню, добавить кастомные функции к таблице или как-либо еще изменить / дополнить стандартное поведение таблицы, можно добавить скрипт в эту директорию.

    Необходимо соблюсти 2 момента:

    1. В профайле клиентсокого объекта таблицы поставить галочку "Additional functionality".

    2. Назвать js файл также как назвается клиентский объект.

  2. Формы ../forms

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

    Таким образом, необходимо создать директорию которая будет называться также как клиентский объект формы. Внутри этой директории создать 2 .html файла и 2 .js файла.

    Для файлов отвечающих за форму создания в конце надо добавить "_add"

    ../form_courier
    ---- form_courier.html
    ---- form_courier.js
    ---- form_courier_add.html
    ---- form_courier_add.js

  3. Фреймы ../frames

    Для того чтобы ваш фрейм работал, помимо клиентского объекта, у него должны быть верстка и скрипт.

    Файлы фрейма должны лежать в своей директории, директория должна называться так же как клиентский объект фрейма.
    Сами файлы также должны называть как клиентский объект .html и .js.

Uploads

/public/uploads/..


В системе есть 2 места куда попадают файлы загруженные пользователями:

  1. Данная директория не приватная, то есть файлы будут доступны если запросить их с клиента указав путь к ним.
  2. Приватная директория (serverUploads), приватная директория для хранения важных документов, чтобы к ним не было доступа извне, работа с данной директорией описана ниже в документации.

Обзор директорий - бекэнд

Classes - Классы



/classes/..


Директория в которой лежат все файлы классов, базовые классы платформы лежат в поддиректории ../system/

Все классы в системе наследуются от основного, BasicClass, обеспечивающего все необходимые методы, такие как add, modify, remove и пр.

Файлы для добавленных вами классов создаются автоматически в этой директории, единственное что необходимо сделать руками - добавить их в git.

Config - конфиги.



/config/..

В директории config лежит единственный конфигурационной файл, который определяет все базовые настройки системы:

lang: "en" / "ru" - Отвечает за языковую версию платформы GoCore

isDeveloper: false - Настройка ВАНЯ

port: 8080 - Порт на котором будет запущена система.

host: "localhost" - Хост на котором будет запущена система.

session: {...} - Настройка сессии ВАНЯ
-- secret: "ВАНЯ"
-- key: "ВАНЯ"
-- cookie: {...} - "ВАНЯ"
-- -- path: "ВАНЯ"
-- -- httpOnly: "ВАНЯ"
-- -- maxAge: "ВАНЯ"

maxProcess: 32 - ВАНЯ

mysqlConnection: {...} - Конфигурация подключения к БД.
-- connectionLimit: 100 - ВАНЯ
-- connectTimeout: 60000 - ВАНЯ
-- acquireTimeout: 60000 - ВАНЯ
-- port: 3306 - ВАНЯ
-- host: "localhost" - ВАНЯ
-- user: "" - Имя пользователя для подключения к БД.
-- password: "" - Пароль для доступа к БД.
-- database: "empty" - ВАНЯ.
-- dateStrings: "TIMESTAMP" - ВАНЯ.

mail: {...} - Конфигурация подключения к почтовому серверу.
-- mailTransport: {...} - ВАНЯ
-- -- host: "smtp.mail.ru" - ВАНЯ
-- -- port: "465" - ВАНЯ
-- -- debug: true - ВАНЯ
-- -- secure: true - ВАНЯ
-- -- auth: {...} - Авторизационные данные для почтового сервера.
-- -- -- user: Имя пользователя
-- -- -- pass: Пароль
-- -- from: "your@mail.ru" - От кого отправлять письма, ВАНЯ
-- -- notificationEmail: "your@mail.ru,your_developer@mail.ru" - Почтовые адреса для уведомлений системы, можно указывать через запятую. ВАНЯ
-- feedbackEmail: "your@mail.ru" - Обратный адрес, ВАНЯ

DB - База данных

/DB/..


В директории хранится основной дамп базы для первого запуска системы.

Также, в поддиректории ../UPDATE_SCRIPTS/ лежат различные заготовки SQL скриптов для ряда популярных операций.

libs - Системные библиотеки - ВАНЯ

/libs/..


В директории хранится ... ВАНЯ

middleware

/middleware/..


В директории хранится ... ВАНЯ

Models - Что это ВАНЯ

/models/..


В директории хранится ... ВАНЯ

Modules - Что это ВАНЯ

/modules/..


В директории хранится ... ВАНЯ

Node modules - Директория для npm

/node_modules/..


В директории хранятся все библиотеки установленные через npm.

Роутинг - Директория для ... ВАНЯ

/routes/..


В директории хранятся ... ВАНЯ

Приватный uploads

/server_uploads/..


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

Socket

/socket/..


В директории хранятся ... ВАНЯ

Шаблоны

/templates/..


В директории хранятся файлы-шаблоны для различных отчетов и уведомлений, шаблоны собираются на mustache.js.

Разработка

Проектирование


Когда у вас уже есть примерное понимание как будет выглядеть архитекура классов вашего проекта можно заложить ее в платформу через файл tables.json, именно с него начинается разработка в GoCore.



Архитектура БД, tables.json, tablesCore.json


Tables.json это файл в котором описаны ваши классы и их поля.

Также, существует файл tablesCore.json, в котором описаны базовые классы платформы, например User или Company. Такие классы ничем не отличаются от тех что создадите вы, просто для удобства описаны в отдельном файле.

Правила записи в tables.json


Посмотрите видеоуроки:

По ссылке таблица c правилами оформления tables.json.

Классы

Создание классов, синхронизация с tables.json


После того как вы описали ваши классы в tables.json, можно переходить к их созданию в системе, для этого:

  1. Зайдите в Settings -> Classes.
  2. Создайте новую запись в таблице, кнопка (Create).
  3. В поле "name" укажите название вашего класса из tables.json, который хотите завести в системе.
  4. Сохраните таблицу нажав "Save".
  5. Кликните правой клавишей по созданой строке, выберите пункт "Синхронизировать с tables.json"

По клику на "Синхронизировать с tables.json" произойдет следующее:

  1. Система подтянет описание класса из файла tables.json.
  2. Создаст все необходимые записи касательного нового класса в БД.
  3. Исходя из типов данных, описанных в tables.json, предустановит полям класса правильные типы редакторов и прочие настройки профайла класса.
  4. Система автоматически создаст одноименный пункт меню в Temporary, по которому будет открываться таблица основанная на данном классе.
  5. Система автоматически создаст одноименный файл класса на бекэнде, в директории /classes. Именно в этом файле вам предстоит в дальнейшем программировать бизнес-логику.
  6. Не забудьте добавить его в git.

Настройка классов.



Настройка класса состоит из 2-х частей, настройка профайла класса и настроки полей.

Настройка профайла класса:
  1. child_client_object: Поле для указания дочернего клиентского объекта, например, когда надо отобразить таблицу внутри формы.

  2. open_form_client_object: Поле для указания формы, которая будет открываться по клику на "Open" из контекстного меню таблицы данного класса.

  3. row_max_num: Количество записей в таблице по умолчанию на одной странице пагинации.

  4. default_order_by: Порядок вывода по умолчанию, сюда можно указать любое поле класса. ВАНЯ

  5. default_where: Where по умолчанию, которое будет добавляться к запросу по данному классу. ВАНЯ (Правила оформления)

  6. new_command: Разрешить / запретить создание записей в данном классе.

  7. modify_command: Разрешить / запретить изменение записей в данном классе.

  8. remove_command: Разрешить / запретить удаление записей в данном классе.

  9. additional_functionality: Галочка, отвечающая за подключение кастомного клиентского .js файла.

    Для того, чтобы описать дополнительный функционал к таблице класса, необходимо установить галочку и создать одноименный классу .js файл в директории /public/html/tables/require

Настройка полей класса:
  1. sort_no: Номер сортировки, по данному полю сортируется порядок вывода колонок в таблице класса.
    Номер сортировки можно менять руками или использовать контекстное меню "Set column position", функция установит колонку на позицию которую вы укажите, и автоматически переопределит sort_no последующим колонкам.

  2. id: id

  3. name: Имя поля для пользователя.

  4. column_name: Системное имя поля.

  5. hint: Подсказка по наведению на поле, которая будет всплывать в таблицах, формах и фреймах класса.

  6. Класс: Класс к которому относится данное поле.

  7. primary_key: Первичный ключ, по умолчанию id.

  8. parent_key: Родительский ключ. ВАНЯ

  9. visible: Видимость поля, если галочку снять поле не будет показано в таблицах, формах и фреймах данного класса.

  10. queryable: ВАНЯ

  11. whereable: ВАНЯ

  12. required: Обязательное поле, если поставить галочку, таблицы, формы и фреймы будут ругаться при попытке сохранить их не заполнив данное поле.

  13. is_unique: ВАНЯ

  14. quick_search_field: Поля, отмеченные галочкой quick_search_field попадают в перечень полей по которым происходит поиск при исользовании "Быстрого поиска" в таблицах.

  15. editable: Редактируемое поле, если галочка снята - поле нельзя будет редактировать.

  16. server_editable: ВАНЯ

  17. insertable: ВАНЯ

  18. server_insertable: ВАНЯ

  19. updatable: ВАНЯ

  20. server_updatable: ВАНЯ

  21. default_value: Значение по умолчанию.

  22. Тип редактора: Выбор типа редактора для колонки, в случае выпадающего списка необходимо также установить следующий параметр "Класс колонки", к какому классу обращается запрос для получения данных в списке.

  23. Класс колонки: Для выпадающих списков, необходимо указать к какому классу обращается данное поле чтобы подгрузить данные в список.

  24. Тип фильтра: Если установить тип фильтра для поля, он появится в блоке фильтрации таблицы.

  25. Вернуть id для select: ВАНЯ

  26. Вернуть name для select: ВАНЯ

  27. Сохранять в колонку для select: ВАНЯ

  28. lov_columns: ВАНЯ

  29. select_search_columns: ВАНЯ

  30. validation: ВАНЯ

  31. get_formating: ВАНЯ

  32. set_formating: ВАНЯ

  33. is_virtual: Признак "Виртуальное поле", для полей которые подтягивают данные из связанных таблиц а не хранятся в классе напрямую.

  34. from_table: Поле для связанных таблиц, параметр указывает из какого класса данное поле подтягшивает данные.

  35. keyword: Поле для связанных таблиц, параметр указывает по занчению какого поля из текущего класса получить id из внешнего класса. ВАНЯ

  36. return_column: Поле для связанных таблиц, параметр указывает какое поле вернуть из внешнего класса.

  37. concat_fields: Конкатенированные поля, поле может содержать в себе значения из нескольких полей текущего класса разедляя запятыми все блоки составного поля (в том числе пробелы и символы), например так: "courier_firstname, ,courier_lastname".
    Внимание! Конкатенированные поля не могут собираться из виртуальных полей напрямую, предварительно их необходимо определить в текущем классе. ВАНЯ

  38. type: Тип данных, то что вы указываете на этапе tables.json (varchar, bigint...)

  39. field_length: Длина поля, то что вы указываете на этапе tables.json.

  40. join_table: Поле для связанных таблиц, параметр указывает через какую таблицу обращаться к конечной таблицы из которой подтягиваются данные. ВАНЯ

  41. modify_in_ext_tbl: ВАНЯ

  42. modify_in_ext_tbl_key: ВАНЯ

  43. table_alias: Поле для связанных таблиц, параметр указывает alias подтягиваемых данных в случае если данные необходимо подтянуть несколько раз из одной и той же внешней таблицы. ВАНЯ

  44. join_table_by_alias: ВАНЯ

  45. min_value: Минимальное значение для полей типа number.

  46. max_value: Максимальное значение для полей типа number.

  47. value_step: Шаг значений для полей типа number.

  48. Поля для дозаполнения: ВАНЯ

  49. dynamic_field_id: ВАНЯ

  50. id_from_source: ВАНЯ

  51. dynamic_field_pair_id: ВАНЯ

  52. is_class_field: ВАНЯ

  53. source_class_id: ВАНЯ

  54. is_co_field: ВАНЯ

  55. source_class: ВАНЯ

  56. table_for_filter: ВАНЯ

  57. parent_key_for_filter: ВАНЯ

  58. record_key_for_filter: ВАНЯ

  59. input_key_for_filter: ВАНЯ

  60. table_value_name_prefix: ВАНЯ

  61. is_inherit: ВАНЯ

  62. save_log: ВАНЯ

  63. depend_column: ВАНЯ

  64. min_datetime_value: Минимальное значение для полей типа дата/время, заполняются по правилам: ВАНЯ

  65. max_datetime_value: Максимальное значение для полей типа дата/время, заполняются по правилам: ВАНЯ

  66. default_datetime_value: Значение по умолчанию для полей типа дата/время, заполняются по правилам: ВАНЯ

  67. calender_options: ВАНЯ

  68. is_depend_where_func: ВАНЯ

  69. Created: Дата/время создания поля.

  70. Updated: Дата/время обновления поля.

  71. Removed: Дата/время удаления поля.

  72. Published: Дата/время публикации поля.

Файлы классов

Все классы лежат в директории /classes/

ВАНЯ, что-то еще надо сказать?

Зависимости:


Подключение зависимостей: В первом блоке кода подключены зависимоти, базовые классы, npm модули, а также модули которые будут написаны вами.


let MyError = require('../error').MyError; // Модуль ошибок для внутреннего дебага let UserError = require('../error').UserError; // Модуль ошибок для вывода ошибок на клиент let UserOk = require('../error').UserOk; // Модуль успешного ответа let BasicClass = require('./system/BasicClass'); // Базовый класс let util = require('util'); // ВАНЯ let async = require('async'); // Библиотека async let rollback = require('../modules/rollback'); // Модуль роллбеков let funcs = require('../libs/functions'); // ВАНЯ let fs = require('fs'); // Модуль работы с файловой системой let mustache = require('mustache'); // Библиотека Mustaсhe для шаблонизации let sendMail = require('../libs/sendMail'); // Модуль отправки писем

Наследование:


Определение наследования для текущего класса от BasicClass (Базового класса): Для команд get, add, modify, remove, getForSelect. - ВАНЯ


ВАНЯ - Комменты к строкам var Model = function(obj){ this.name = obj.name; this.tableName = obj.name.toLowerCase(); var basicclass = BasicClass.call(this, obj); if (basicclass instanceof MyError) return basicclass; }; util.inherits(Model, BasicClass); Model.prototype.getPrototype = Model.prototype.get; Model.prototype.addPrototype = Model.prototype.add; Model.prototype.modifyPrototype = Model.prototype.modify; Model.prototype.removePrototype = Model.prototype.remove; Model.prototype.getForSelectPrototype = Model.prototype.getForSelect;

Переопределение:


Переопределение базовых методов: init, get, add, modify, remove, removeCascade и getForSelect таким образом, что:

  1. Каждый базовый метод по умолчанию наследуется от родителя.
  2. Если объявить базовый метод и добавить к конце "_" (Например "Model.prototype.add_"), этот метод будет исполняться вместо базового.
  3. Также можно переопределять методы для конкртеных клиентских объектов основанных на данном класее, для этого необходимо добавить к названию метода "_table_courier" (Нижнее подчеркивание и название клиентского объекта, например Model.prototype.add_table_courier)
Базовые методы стирать не нужно, просто добавляейте свои, переопределнные.

Model.prototype.init = function (obj, cb) { if (arguments.length == 1) { cb = arguments[0]; obj = {}; } if (typeof cb !== 'function') throw new MyError('В метод не передан cb'); // The method is not passed to cb if (typeof obj !== 'object') return cb(new MyError('В метод не переданы obj')); // The method is not passed to obj var _t = this; Model.super_.prototype.init.apply(this, [obj , function (err) { cb(null); }]); }; Model.prototype.get = function (obj, cb) { if (arguments.length == 1) { cb = arguments[0]; obj = {}; } var _t = this; var client_object = _t.client_object || ''; var coFunction = 'get_' + client_object; if (typeof _t[coFunction] === 'function') { _t[coFunction](obj, cb); } else { if (typeof _t['get_'] === 'function') { _t['get_'](obj, cb); } else { _t.getPrototype(obj, cb); } } }; Model.prototype.add = function (obj, cb) { if (arguments.length == 1) { cb = arguments[0]; obj = {}; } var _t = this; var client_object = _t.client_object || ''; var coFunction = 'add_' + client_object; if (typeof _t[coFunction] === 'function') { _t[coFunction](obj, cb); } else { if (typeof _t['add_'] === 'function') { _t['add_'](obj, cb); } else { _t.addPrototype(obj, cb); } } }; Model.prototype.modify = function (obj, cb) { if (arguments.length == 1) { cb = arguments[0]; obj = {}; } var _t = this; var client_object = _t.client_object || ''; var coFunction = 'modify_' + client_object; if (typeof _t[coFunction] === 'function') { _t[coFunction](obj, cb); } else { if (typeof _t['modify_'] === 'function') { _t['modify_'](obj, cb); } else { _t.modifyPrototype(obj, cb); } } }; Model.prototype.remove = function (obj, cb) { if (arguments.length == 1) { cb = arguments[0]; obj = {}; } var _t = this; var client_object = _t.client_object || ''; var coFunction = 'remove_' + client_object; if (typeof _t[coFunction] === 'function') { _t[coFunction](obj, cb); } else { if (typeof _t['remove_'] === 'function') { _t['remove_'](obj, cb); } else { _t.removePrototype(obj, cb); } } }; Model.prototype.getForSelect = function (obj, cb) { if (arguments.length == 1) { cb = arguments[0]; obj = {}; } var _t = this; var client_object = _t.client_object || ''; var coFunction = 'getForSelect_' + client_object; if (typeof _t[coFunction] === 'function') { _t[coFunction](obj, cb); } else { if (typeof _t['getForSelect_'] === 'function') { _t['getForSelect_'](obj, cb); } else { _t.getForSelectPrototype(obj, cb); } } };

Свои методы:


После определенных базовых методов класса размещены 2 примера. Их можно скопировать и на их основе написать свой метод.


Model.prototype.exampleGet = function (obj, cb) { if (arguments.length === 1) { cb = arguments[0]; obj = {}; } var _t = this; var id = obj.id; if (isNaN(+id)) return cb(new MyError('Не передан id',{obj:obj})); // Not passed to id let data; async.series({ },function (err, res) { if (err) return cb(err); cb(null, new UserOk('noToastr',{data:data})); }); }; Model.prototype.example = function (obj, cb) { if (arguments.length === 1) { cb = arguments[0]; obj = {}; } var _t = this; var id = obj.id; if (isNaN(+id)) return cb(new MyError('Не передан id',{obj:obj})); // Not passed to id var rollback_key = obj.rollback_key || rollback.create(); var doNotSaveRollback = obj.doNotSaveRollback || !!obj.rollback_key; async.series({ },function (err, res) { if (err) { if (doNotSaveRollback) return cb(err); rollback.rollback({obj:obj, rollback_key: rollback_key, user: _t.user}, function (err2) { return cb(err, err2); }); } else { //if (!doNotSaveRollback){ // rollback.save({rollback_key:rollback_key, user:_t.user, name:_t.name, name_ru:_t.name_ru || _t.name, method:'METHOD_NAME', params:obj}); //} cb(null, new UserOk('Ок')); } }); };

Уравление ошибками:


ВАНЯ ВАНЯ


СЮДА КОД

Уравление роллбеками:


ВАНЯ ВАНЯ


СЮДА КОД

Как пользоваться Async:


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


СЮДА КОД

Клиентские объекты

Видеоурок по клиентским объектам:

  1. Клиентские объекты в GoCore это различные виды отображения и взаимодействия на базе класса.
  2. Клиентский объект это таблица, форма или фрейм.
  3. На базе одного класса может быть создано неограниченное количество клиентских объектов.
  4. Клиентский объект имеет свой собственный профайл, скопированный с профайла класса, который можно изменять.
  5. Профайл клиентского объекта, в случае невозможности найти тот или иной параметр у себя - наследует его у профайла класса.
  6. Существуют правила наименования клиентских объектов, их название должно начинаться с ключевого слова "table_", "form_" или "frame_", в зависимости от типа.
    После обязательного префикса можно называть клиентский объект в на свое усмотрение, старайтесь давать адекватные имена содержащие в себе название родиетельского класса и четко отражающие назначение / поведение клиентского объекта, например "table_order_cancelled" или "form_user_readonly".
  7. ВАНЯ - мб что-то еще умное написать?

Создание и настройка:

  1. Для создания клиентского объекта необходимо зайти в Settings -> Client objects;
  2. Создать новую запись в таблице, нажав на "Create";
  3. Указать название (name) клиентского объекта (префикс "table_", "form_", "frame_" + "название класса_" + "отличительные особенности если они есть", если нет то достаточно просто указать "table_courier")
  4. Указать класс клиентского объекта (class) из выпадающего списка;
  5. Сохранить таблицу, кнопка "Save"
  6. Вызвать контекстное меню и кликнуть "Синхронизировать с классом".



Если вы только создаете клиентский объект, во всплывшем окне ничего менять не нужно, просто нажать "Синхронизровать".

Оданако, если вы повторно синхронизируете клиенсткий объект с классом (например если расширился или изменился класс), вы сможете управлять синхронизацией, а именно:

  1. Указать поля которые вы хотите синхронизировать, остальные поля останутся без изменений. Для этого вместо * укажите поля через запятую.
  2. Удалять поля из клиентского объекта если они были удалены в классе, для этого поставьте галочку "Удалять поля".
  3. Удалять физически - ВАНЯ

После синхронизации с классом, профайл клиентского объекта готов к работе. Вы можете зайти в него и настроить все что нужно по образу и подобию того как вы это делали в профайле класса.

Файлы клиентских объектов


Лежат в /public/html/..
  1. Таблицы ../tables/require

    По умолчанию таблицы работают без дополнительных скриптов, однако, если вам нужно сделать контекстное меню, добавить кастомные функции к таблице или как-либо еще изменить / дополнить стандартное поведение таблицы, можно добавить скрипт в эту директорию.

    Необходимо соблюсти 2 момента:

    1. В профайле клиентсокого объекта таблицы поставить галочку "Additional functionality".

    2. Назвать js файл также как назвается клиентский объект.

  2. Формы ../forms

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

    Таким образом, необходимо создать директорию которая будет называться также как клиентский объект формы. Внутри этой директории создать 2 .html файла и 2 .js файла.

    Для файлов отвечающих за форму создания в конце надо добавить "_add"

    ../form_courier
    ---- form_courier.html
    ---- form_courier.js
    ---- form_courier_add.html
    ---- form_courier_add.js

  3. Фреймы ../frames

    Для того чтобы ваш фрейм работал, помимо клиентского объекта, у него должны быть верстка и скрипт.

    Файлы фрейма должны лежать в своей директории, директория должна называться так же как клиентский объект фрейма.
    Сами файлы также должны называть как клиентский объект .html и .js.

Синхронизация с классом и tables.json


Как описано выше, клиентский объект можно синхронизировать с классом, а в самом начале мы писали о том что класс синхронизируется с tables.json.

ВАЖНО! Когда вы хотите добавить новое поле в класс или поменять его (важные параметры - ВАНЯ), необходимо делать это начиная с tables.json а не создавать новые поля в профайлах напрямую.

  1. Дополнить файл tables.json.
  2. Синхронизировать класс с tables.json.
  3. Синхронизировать клиенсткий объект с классом.

Таблицы


Для создания кастомного функционала таблиц есть ряд возможностей, рассмотрим на простом примере table_courier.js:

(function () { let tableInstance = MB.Tables.getTable(MB.Tables.justLoadedId); tableInstance.ct_instance.ctxMenuData = [ { name: 'option0', title: 'Открыть', disabled: function(){ return false; }, callback: function(){ tableInstance.openRowInModal(); } }, { name: 'option1', title: 'Кастомная функция', disabled: function () { return false; }, callback: function () { let row = tableInstance.ct_instance.selectedRowIndex; let id = tableInstance.data.data[row]['id']; let o = { command: 'run_custom_method', object: 'courier', params: { id: id } }; socketQuery(o, function(res){ if(!res.code) console.log('Ok!'); }); } } ]; }());

Итак, все по порядку:

  1. 1 строка: Код должен быть оберунт в самовызывающуюся функцию, (function(){ your code }())

  2. 4 строка: Объявление переменной tableInstance, которая свяжет текущий файл с клиентским объектом, его данными и профайлом.

  3. 6 строка: Переопределение контекстного меню.

    ВАЖНО! Если вы используете подключаемый файл и ставите галочку "additional_functionality" в профайле клиентского объекта, контекстное меню "Open" не будет работать по умолчанию, его необходимо прописать в подключенном файле.

    Контекстное меню "ctxMenuData" является объектом клиенского класса отображения таблиц, описанного в /public/assets/js/classicTable/classicTable.js, и имеет следующие параметры:

    1. name: Наименование пункта меню, должны быть уникальными в рамках одного меню.
    2. title: Название пункта меню которе будет видеть пользователь.
    3. disabled: Функция, возвращающая true / false, отвечает за доступность пункта меню.
    4. callback: Функция, которая срабатывает по клику на пункт меню.
  4. 25,26 строка: Получение данных выбранной строки. Подробнее о структуре данных и глобальных переменных ниже в документации.

  5. 28 - 34 строка: Подготовка объекта запроса к серверу. Подробнее о запросах, ответах и where ниже в документации.

  6. 36 - 40 строка: Отправка запроса на сервер и обработка ответа.

Помимо контекстного меню вы можете писать любой кастомный код используя доступ к профайлу, данным и функциям и методам файлов TableNew.js и classicTable.js, подробнее о них - ниже в документации.

Формы

Видеоурок по функциям формы:


Верстка формы:

В формах встроен шаблонизатор, который позволяет встраивать поля клиентского объекта просто и быстро, для отображения поля достаточно написать его в 3-х фигурных скобках {{{column_name}}}.
Для того чтобы вывести только значение поля, укажите его следующим образом: {+{column_name}+}

В GoCore подключен bootstrap, можно пользоваться всеми его преимуществами.

Типичная верстка простой формы выглядит так:




                        

Рассмотрим подробно:

2 строка: Блок с классом "insertIntoHeader", автоматически встраивается в заголовок формы и является переключателем табов внутри формы.
Также туда может бысть втроен любой другой контент.

3,4 строки: Табы, у переключателей должен быть класс "modal_tab_switcher" и уникальный атрибут "data-tab", переключается класс "active".

7 строка: Блок с первым табом, должен иметь класс "modal_tab" и атрибут "data-tab" соответсвтующий переключателю.

10 строка: Заголовок формы, "Курьер" и названия полей в формате только значение {+{name}+}.

16 - 19 строки: Поля клиентского объекта.

49 строка: Блок для подгрузки таблицы в форму, чтобы таблица подгрузилась необходимо соблюсти следующие правила:

  1. У блока должен быть класс "fn-child-tbl-holder"
  2. У блока должен быть атрибут "data-tbls", в котором будет указаны название класса подгружаемой таблицы и, через точку, клиентский объект таблицы, например data-tbls="user.table_user".
    Таких подключений может быть несколько в одном блоке, для этого указывайте пары класс.клиентский_объект через запятую, например data-tbls="user.table_user,courier.table_courier".
    В случе если в рамках одного блока будет подтянуто несколько таблиц, система автоматически сделает табы между которыми удобно переключаться.
  3. В профайле формы, в поле "child_client_object" должны быть указаны все пары класс.клиентский_объект через запятую, "user.table_user,courier.table_courier".

53,54 строки: Блок для размещения кастомных кнопок в форме, описание которых будет ниже в документации. Два блока с классами "lower-buttons-padder" и "lower-buttons-wrapper".



Вот так форму видит пользователь:



Скрипт формы:

Рассмотрим файл form_courier.js

(function () { const formID = MB.Forms.justLoadedId; const formInstance = MB.Forms.getForm('form_courier', formID); const formWrapper = $('#mw-' + formInstance.id); formInstance.lowerButtons = [ { title: 'Заполнить координаты', color: "blue", icon: null, type: "SINGLE", hidden: false, condition: [], handler: function() { // some handler } }, { title: 'Отправить накладную курьеру', color: "blue", icon: null, type: "SINGLE", hidden: false, condition: [], handler: function() { // some handler } } ]; let courier = { init: function(){ courier.initMap(); }, initMap: function(){ let from_lat = formInstance.data.data[0].home_latitude; let from_lng = formInstance.data.data[0].home_longitude; if(!formInstance.map_inited){ this.Lmap = L.map('courier-map-container', { center: [from_lat, from_lng], zoom: 5 }); L.tileLayer('http://{s}.tile.osm.org/{z}/{x}/{y}.png').addTo(this.Lmap); this.Lmap.setView([from_lat, from_lng], 11); setTimeout(()=>{ this.Lmap.invalidateSize(); this.Lmap.inited = true; console.log('MAP INITED'); let blueIcon = new L.Icon({ iconUrl: 'https://cdn.rawgit.com/pointhi/leaflet-color-markers/master/img/marker-icon-2x-blue.png', shadowUrl: 'https://cdnjs.cloudflare.com/ajax/libs/leaflet/0.7.7/images/marker-shadow.png', iconSize: [25, 41], iconAnchor: [12, 41], popupAnchor: [1, -34], shadowSize: [41, 41] }); let marker_1 = L.marker([from_lat, from_lng], {icon: blueIcon}).addTo(this.Lmap); formInstance.map_inited = true; }, 500); } } }; courier.init(); }());

2 строка: Код формы должен быть обернуть в самоисполняющуюся функцию, (function(){ ..yourCode.. }());

3,3,4 строки: Привязка скрипта к вызванному клиентскому объекту (formID), получения инстанса формы (formInstance) и определение его контейнера (formWrapper).

7 строка: Определение массива объектов formInstance.lowerButtons, описывающего кнопки формы. Описание одной кнопки состоит из:

  1. title: Название кнопки.

  2. color: Цвет кнопки, возможные значения: red, gree, blue, grey, black. Вы можете добавить свои цвета просто дописав к ним стили.

  3. icon: Иконка, необходимо выбрать иконку из fontawesome, указать класс "fa fa-check".

  4. type: Вид кнопки, может быть "SINGLE" или "DOUBLE", в зависимости от типа будет отображены разыне стили кнопок.

  5. hidden: Признак видимости кнопки, значение может быть булевым или функцией, возвращающей true/false.

  6. condition: Состояние кнопки, доступна или недоступна. Значение принмает массив объектов следующего вида:

    [{ colNames: ['order_status_sysname'], matching: ['not_equal'], colValues: ['COURIER_SELECTED'] }]

    colNames: Наименования полей в зависимости от значения которых мы хотим определить доступность кнопки.
    matching: Типа сравнения, 'equal' - равно значению, 'not_equal' - не равно значнию.
    colValues: Значения, с которыми мы хотим сравнить текущее значение интересующих нас полей.

    В результате сравнения по указанным параметрам в значение condition вернется true или false.

    Также, можно указывать более одного сравнения, через запятую, например:

    [{ colNames: ['order_status_sysname','cargo_type_sysname'], matching: ['not_equal','not_equal'], colValues: ['COURIER_SELECTED','OVERSIZE'] }]

    В таком случае система проведет проверки по всем условиям, сравнивая их между собой через AND.

  7. handler: Функция, выполняющаяся по клику на кнопку.

36 - 72 строки: Кастомный код, описывающий поведение формы, в данном случае инициализацию карты.



Фреймы



ВАНЯ

Настройка меню

Управление меню рамположено в System -> Menu Editor



Рассмотрим поля которые необходимо заполнять / редактировать:
  1. Name: Наименование пункта меню.

  2. Visible: Видимость пункта меню.

  3. Пункт меню: Системное название пункта меню, должно быть уникальным.

  4. Menu type: Тип меню, бывают: "Родительский", "Родительский активный", "Элемнет", "Отчет".

    1. Родительский: Родительская категория меню, служит контейнером для подпунктов (Элементов).
    2. Родительский активный: Находится на уровне родительских категорий, однако сама является активным элементом, который открывает клиентский объект или класс.
    3. Элемент: Пункт меню, открывает клеинтский объект или класс.
    4. Отчет: Специальный тип меню для вызова отчетов.
  5. Иконка: Иконка для меню, отображается только на уровне родительских категорий.

  6. Родительский элемент: Поле определяет внутри какого пункта меню будет располагаться текущий элемент меню.

  7. Класс: Класс вызываемой по клику сущности.

  8. Клиентский объект: Клиентский объект вызываемой по клику сущности.

API - Запросы, ответы, where, ошибки.

Посмотрите видеоурок:

Введение

В GoCore API взаимодействия работает по одинаковым стандартам для общения между:

  1. Клиентом и сервером.
  2. Сервером и базой данных.
  3. Внешним API и сервером.
  4. Между версией GoCore для сайта и сервером.

Все запросы работают с использованием технологии Socket.io

Запросы


Чтобы отправить запрос необходимо вызвать функцию socketQuery, передать в нее объект с параметрами запроса и получить ответ от сервера в колбэк функции socketQuery.

Например:

let o = { command: 'get', object: 'courier', params: { } } socketQuery(o, function(res){ if(!res.code){ console.log('Success', res) } });
Этот код обратится к методу get класса Courier и в случае если в код ответа придет "0", напишет в консоль "Success" и тело ответа.

Рассмотрим еще один кейс:

let o = { command: 'get', object: 'courier', client_object: 'table_courier' params: { } } socketQuery(o, function(res){ if(!res.code){ console.log('Success', res) } });
Здесь добавлен параметр 'cleint_object', он позволяет запрашивать данные клиентского объекта, принимая во внимания настройки его профайла.
Также, если в файле класса метод перезаписан для данного клиентского объекта (get_table_courier), будет выполнен именно он, вместо стандартного 'get'.


Параметры (params):


let o = { command: 'get', object: 'courier', params: { param_where: {}, where: [], limit: 1, page_no: 1, sort: {} } } socketQuery(o, function(res){ if(!res.code){ console.log('Success', res) } });
  1. param_where: Короткая запись where, это объект ключ:значение, например:

    param_where: { name: 'Иван', age: 25 }
    Такая запись запросит всех курьеров у которых 'name' равен 'Иван' и 'age' равен 25.

  2. where: Полная запись where, это массив объектов, где каждый объект - условие запроса.
    Ключи внутри объекта:

    1. key: Ключ, наименование поля по которому хотим наложить условие.
    2. type: Тип сравнения, передаваемого значения с данными. Бывают следующие типы сравнения:
      '=' Равно, значение по умолчанию.
      '<' Меньше.
      '>' Больше.
      '<=' Меньше или равно.
      '>=' Больше или равно.
      '!=' или '<>' Не равно.
      'LIKE' Ищет вхождение в искомую строку.
      '%LIKE' Ищет такое вхождение, которое заканчивается на искомую строку.
      'LIKE%' Ищет такое вхождение, которое начинается на искомую строку.
      'IN' Ищет вхождение в массив.
      'NOTIN' или '!IN' Определяет отсутствие в массиве.
      'BETWEEN' Ищет между двумя значениями.
      'ISNULL' Значение является NULL.
      'ISNOTNULL' Значение не является NULL.

      ВАНЯ ПРОВЕРЬ.
    3. val1: Значение, по которому накладывается условие, почему именно 'val1' а не 'val'? Это связано с тем, что есть еще 'val2' для случаев, когда сравнение происходит оператором 'BETWEEN' и необхоимо передать 2 значения.
    4. val2: Второе значение, используется только для случаев когда тип сравнения 'BETWEEN'.
    5. group: Алиас, для групперовки запросов между собой и определения оператора между ними, 'AND' или 'OR'. Для того чтобы указать оператор сравнения между двумя условиями необходимо присвоить им одинаковое свойство 'group'.
    6. comparisonType: Тип сравнения несольких групп условий,

      ВАНЯ - допиши тут про сравнение внутри группы с один элиасом и про сравнение между группами с разными элиасами

    Пример:

    let o = { command: 'get', object: 'courier', params: { where: [{ key: 'name', type: '=', val1: 'Иван' },{ key: 'age', type: 'BETWEEN', val1: 18, val2: 25 }], } }

    Такой запрос вернет всех курьеров с именем 'Иван' и возрастом в диапазоне от 18 до 25.

    Еще пример:

    let o = { command: 'get', object: 'courier', params: { where: [{ key: 'name', type: '=', val1: 'Иван', group: 'names' },{ key: 'name', type: '=', val1: 'Сергей', group: 'names' }], } }

    Такой запрос вернет всех курьеров с именем 'Иван' или 'Сергей'.

    ВАНЯ НУЖНЫ ЕЩЕ ПРИМЕРЫ С comparisonType

  3. limit: Ограничение по количестку записей в ответе, по умолчанию стоит 1000.

  4. page_no: Номер страницы запрашиваемых данных, например если вы хотите получить записи с 1 по 10, вы просто указываете 'limit' = 10, чтобы запросить следующие 10 записей, вы указываете 'limit' = 10 и 'page_no' = 2.

  5. sort: Объект описывающий сортировку данных:


    sort: { columns: ['name','surname'], directions: ['asc','asc'] } Такие параметры отсортируют данные следющим образом, сначала все будет отсортировано по 'name' А-Я, в тех случаях, где 'name' одинаковый включится сортировка по 'surname' А-Я.

Ответ


Единая структура данных ответа для всех запросов, пример:

{ code: 0, data: [{ id: 'Сергей', surname: 'Прохоров', age: 21 },{ id: 'Анна', surname: 'Голубкова', age: 19 },{ id: 'Георгий', surname: 'Метрофанов', age: 26 }], data_columns: ['id', 'name', 'surname', 'age'], extra_data: { additional_class_fields_profile: {}, count: 3, count_all: 10 }, time: 1 }
Рассмотрим подробно:

3 строка: code - Код ответа, бывают следующие коды:

0: Все ок.
-4: Пользователь не авторизован.
10: Необходимо подтверждение операции пользователем.
101: Запрос не прошел серверную валидацию, как правило, на modify когда есть незаполненные required поля.

4 - 16 строки: data - Данные, массив объектов в котором каждый объект это одна запись запрашиваемой сущности, ее поля и их значения.

17 строка: data_columns - Колонки (Поля), массив названий полей которые есть в запрашиваемой сущности.

18 - 22 строки: extra_data - Дополнительные данные, здесь хранится доп. полезная информация, количество записей полученных по запросу (count) и количество записей всего в данной сущности (count_all).

23 строка: time - Время выполнения запроса на сервере, без учета транспортировки данных.



Рассмотрим другой популярный запрос, профайла таблицы, например, заказов:


let o = { command: "getProfile", object: "order_", client_object: "table_order", params: {} } Ответ: let o = { code: 0, data: [ { calender_options: "", class: "order_", class_id: 858, column_name: "id", concat_fields: "", created: "2020-04-11 21:05:45", created_by_user: "Alexandr", created_by_user_id: 3, default_datetime_value: "", default_value: "", deleted: "", deleted_by_user: "", deleted_by_user_id: "", depend_column: "", dynamic_field_id: "", dynamic_field_pair_id: "", editable: false, ext_company: "MAIN", ext_company_id: 1, ext_data: "", ext_id: "", ext_system_alias: "", field_length: 20, filter_type: "", filter_type_id: "", from_table: "", get_formating: "", hint: "", id: 21493, id_from_source: "", input_key_for_filter: "", insertable: false, is_class_field: false, is_co_field: false, is_depend_where_func: false, is_inherit: false, is_unique: false, is_virtual: false, join_table: "", join_table_by_alias: "", keyword: "", lov_columns: "", lov_return_to_column: "", max_datetime_value: "", max_value: "", min_datetime_value: "", min_value: "", modify_in_ext_tbl: false, modify_in_ext_tbl_key: "", name: "id", parent_key: false, parent_key_for_filter: "", primary_key: true, published: "2020-04-11 21:05:45", queryable: true, quick_search_field: false, record_key_for_filter: "", remove_comment: "", required: false, return_column: "", return_id: "", return_name: "", save_log: false, select_autocomplete_columns: "", select_class: "", select_class_id: "", select_search_columns: "", self_company: "MAIN", self_company_id: 1, server_editable: true, server_insertable: false, server_updatable: false, set_formating: "", sort_no: 10, source_class: "", source_class_id: "", table_alias: "", table_for_filter: "", table_value_name_prefix: "", type: "bigint", type_of_editor: "number", type_of_editor_id: 6, updatable: false, updated: "", validation: "notNull", value_step: 1, visible: true, whereable: true }, { calender_options: "", class: "order_", class_id: 858, column_name: "id", concat_fields: "", created: "2020-04-11 21:05:45", created_by_user: "Alexandr", created_by_user_id: 3, ...etc... } ], data_columns: ["calender_options","class","class_id","column_name","concat_fields","created","created_by_user","created_by_user_id", ...etc...], extra_data: { object_profile: { additional_functionality: true, auto_publish: true, check_company_access: true, check_published: true, checkbox_where: "", checkbox_where_default_enabled: false, checkbox_where_title: "", child_class: "", child_client_object: "", class: "order_", class_id: 858, count_large: false, created: "2020-04-11 21:05:43", created_by_user: "Alexandr", created_by_user_id: 3, current_dynamic_field_alias: "", default_order_by: "id desc", default_where: "", deleted: "", deleted_by_user: "", deleted_by_user_id: "", distinct_columns: "", do_not_set_deep: false, do_not_use_cache_client: false, editable: true, ending: "", ext_company: "MAIN", ext_company_id: 1, ext_data: "", ext_id: "", ext_system_alias: "", hierarchical_table: false, id: 858, like_type: "", modify_command: true, name: "table_order", name_ru: "Заказы", new_command: true, open_form_client_object: "form_order", param_checkbox: "", param_checkbox_default_enabled: false, param_checkbox_title: "", param_checkbox_where: "", param_checkbox_where_default_enabled: null, param_checkbox_where_title: "", parent_key: "", parent_key_index: -1, parent_table: "", prepare_insert: "", primary_key: "id", published: "2020-04-11 21:05:43", remove_command: true, remove_comment: "", rmb_menu: undefined, rows_max_num: 10, rows_max_num_list: "10,20,50,100", self_company: "MAIN", self_company_id: 1, server_parent_key: [], server_parent_key_for_dynamic_fields: "", server_parent_table: [] } }, time: 316, toastr:{ message: "noToastr", title: "Ок", type: "success" } }

В данном примере мы получаем полный профайл клиентского объекта и всех его полей.
  1. code: Код ответа, как в предыдущем примере.
  2. data: Массив объектов, где каждый объект является профайлом одного из полей класса. Все настройки и параметры каждого поля находятся здесь.
  3. data_columns: Массив полей класса.
  4. time: Время исполнения запроса на сервере.
  5. toastr: Специальный объект для всплывающих уведомлений, содержит:
    type: Тип уведомления, бывают:
    Success: Все ок, зеленый.
    Error: Ошибка, красный.
    Info: Инфомационный, синий.
    Warning: Предупреждение, оранжевый.
    title: Заголовок, который увидит пользователь.
    message: Сообщение, которое увидит пользователь.


    В GoCore работает плагин toastr.js, большинство команд, например все add, modify и remove, автоматически уведомляют пользователя о результатах выполнения той или иной операции.

    Если вы хотите написать уведомление сами, просто вставьте toastr[res.toastr.type](res.toastr.title,res.toastr.message) внутри ответа socketQuery.

Ошибки и дебаггинг


В GoCore предусмотрена система управления ошибками, они имеют свои специальные классы ошибок, MyError и UserError.

ВАНЯ

Внешнее API


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

В GoCore предусмотрен специальный интерфейс, где вы сможете быстро описать команды, которые вы предоставляете внешнему миру, помимо описания, тем кто будет работать с вашим API, автоматически будет доступна тестовая среда.

Описание и тестовая среда расположена по адресу http://localhost:8080/protocol/ и выглядит вот так:

Здесь вы можете отобразить все запросы вашего внешнего API, описать их поведение и параметры.

Рассмотрим файл /public/protocol/methods.js в котором описывается протокол:

var methodos = { test: { name: 'User.get_me', name_ru: 'User.get_me', description: 'Вернет информацию о пользоваеле протокола', responseJSON: '' + '\nНет примера\n' + '', o: { command: 'get_me', object: 'User', params: {} } }, createOrder: { name: 'createOrder', name_ru: 'Создать заказ', description: 'Создаст заказ в системе', responseJSON: '' + '\nНет примера\n' + '', o: { command: 'add', object: 'order_', params: { name: { default: 'Бандероль' }, description: { default: 'Позвоните Оле за час до прибытия в вотсап, спасибо!' }, from_address: { default: 'Москва, тимирязевская ул 20' }, to_address: { default: 'Москва, Космонавта волкова 2' }, sender_firstname: { default: 'Оля' }, sender_lastname: { default: 'Петрова' }, sender_phone: { default: '79060635584' }, sender_email: { default: 'mail@mail.ru' }, reciever_firstname: { default: 'Коля' }, reciever_lastname: { default: 'Сидоров' }, reciever_phone: { default: '79060645465' }, reciever_email: { default: 'mail@gmail.com' }, height: { default: '1' }, length: { default: '2' }, width: { default: '3' }, weight: { default: '4' }, date: { default: '13.04.2020' } } } } }

Объект 'methods' описывает команды доступные в вашем API, у каждого метода есть:

  1. name: Название команды.
  2. name_ru: Название команды для пользователя.
  3. description: Описание команды для пользователя.
  4. responseJSON: ВАНЯ
  5. o: Объект, описывающий сам запрос и дефолтные значения полей.

    command: Команда запроса, к какому методу класса будет обращаться запрос.

    object: Класс, к которому обращается запрос.

    params: Параметры запроса, для каждого поля можно указать поле default, оно будет заполняться в поля в интерфейсе тестирования запросов.



ВАЖНО! Перед отправкой любых запросов, необходимо один раз отправить команду User.getMe чтобы авторизоваться.

Фронтэнд

Базовые модули фронтэнд.


TableNew.js

TableNew.js - Это основной клиентский класс обеспечивающий работу таблиц в системе.

/public/assets/js/TableNew.js

Класс обеспечивает все необходимые манипуляции с данными, их получение, преобразование, сохранение и удаление. Работает в связке с classicTable.js, который обеспечивает визуализацию и взаимодействие с различными плагинами (типами редакторов).

Все методы в TableNew.js комментированы на английском языке.

ВАНЯ - Класс транслирует в глобальный скоуп 2 переменные, MB.Tables (Хранилище всех инстансов таблиц) и MB.TableN (Конструктор одного экземпляра класса таблицы)

classicTable.js

classicTable.js - Это основной клиентский класс таблиц обеспечивающий визуализацию и взаимодействие с пользователем.

/public/assets/js/classicTable/classicTable.js

Класс работает в связке с tableNew.js.

Все методы в classicTable.js комментированы на английском языке.

Экзепляр класса classicTable хранится в переменной ct_instance внутри каждого инстанса таблицы класса TableN, чтобы получить доступ к методам и данным необходимо обратится к инстансу MB.Tables.tables[0].ct_instance.

FormNew.js

FormNew.js - Класс обеспечивает все необходимые манипуляции с данными формы, их получение, преобразование, сохранение и удаление. Работает в связке с modalWindows.js, который обеспечивает работу модальных окон в системе.
/public/assets/js/formNew.js

Все методы в formNew.js комментированы на английском языке.

ВАНЯ - Класс транслирует в глобальный скоуп 2 переменные, MB.Forms (Хранилище всех инстансов форм) и MB.FormN (Конструктор одного экземпляра класса формы)

modalWindows.js

modalWindows.js - Класс обеспечивает работу модальных окон в системе. Формы можно двигать, сворачивать и масштабировать.
/public/assets/js/modalWindows.js

Все методы в modalWindows.js комментированы на английском языке.

ФРЕЙМЫ - ВАНЯ


/public/assets/js/...

Меню

За формирование и отрисовку основного меню системы отвечает menurenderer.js.
/public/assets/js/menurenderer.js

Общие скрипты

main.js, onload.js, index.js

/public/assets/js/main.js onload.js index.js

Скрипты, не касающиеся таблиц, форм и фреймов описаны в этих файлах.
Все методы в комментированы на английском языке.

Плагины

Выпадающие списки


/public/assets/js/select3/select3.js
/public/assets/js/......ГДЕ SELECT2 ?

За выпадающие списки в системе отвечают 2 плагина:

  1. select3: Встроенный модуль GoCore обеспечивающий работу с выпадающими списками в связки с таблицами, формами и фреймами.
  2. select2: Внешний плагин, им можно пользоваться для внедрения выпадающих списков которые не относятся к данным вашей системы.

Работа с Select3

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

let selInstace; let parent_id = 15; // id родительского класса let parent_object = MB.Froms.getForm(parent_id, 'form_order'); let selectWrapper = $('#some-wrapper'); let column_name = 'from_metro_station'; let class_name = 'order'; let client_object = 'form_order'; let return_id = 'id'; let return_name = 'name'; let selValue = 1; // Текущее выбранное занчение поля (id) let value = 'Тимирязевская'; // Текущее выбранное занчение поля (name) selInstance = MB.Core.select3.init({ id : MB.Core.guid(), parent_id: parent_id, wrapper: selectWrapper, column_name: column_name, class: class_name, client_object: client_object, return_id: return_id, return_name: return_name, withSearch: true, withEmptyValue: false, absolutePosition: true, isFilter: false, parentObject: parent_object, value: { id: (f.selValue == '') ? 'empty' : selValue, name: (f.value == '') ? '' : value }, additionalClass: '', default_where: [] });

2 строка: Объявление переменной selInstance в которую будет сохранен инстанс выпадающего списка.

4 строка: parent_id - id родительской сущности (класса) внутри которой будет инициализирован выпадающий список.

5 строка: parent_object - ссылка на инстанс родительской сущности (класса) внутри которой будет инициализирован выпадающий список.

7 строка: selectWrapper - jquery селектор контейнера, в который будет помещен выпадающий список.

8 строка: column_name - название поля для которого инициализируется выпадающий список.

9 строка: class_name - Наименование класса, в инстансе которого будет инициализирован выпадающий список.

10 строка: client_object - Наименование клиентского объекта, в инстансе которого будет инициализирован выпадающий список.

11 строка: return_id - Наименование поля, которое будет возвращено как id, из класса, откуда подгружаются данные в выпадающий список.

12 строка: return_name - Наименование поля, которое будет возвращено как name, из класса, откуда подгружаются данные в выпадающий список.

14 строка: selValue - Текущее значение выпадающего списка, id.

15 строка: value - Текущее значение выпадающего списка, name.

17 строка: Инициализация класса выпадающего списка, с параметрами указанными выше.

26 строка: Параметр withSearch - Определяет будет ли выведена строка поиска в выпадающем списке.

27 строка: Параметр withEmptyValue - Определяет будет ли по умолчанию добавлено пустое значение первым пунктом в выпадающем списке.

28 строка: Параметр absolutePosition - Определяет позиционирование (position: absolute / relative) контейнера выпадающего списка.

29 строка: Параметр isFilter - Специальный маркер, для выпадающих списков работающих в фильтрах таблиц.

35 строка: Параметр additionalClass - Наименование класса (css), который будет добавлен к контейнеру выпадающего списка.

36 строка: Параметр default_where - Сюда можно указать where, который будет накладываться на запросы выпадающего списка, where указывается по обычным правилам указанным здесь и является массивм объектов.



Вызов select3 на элемент <select>

Инициализировать select3 можно и на обычный select, просто вызвав его к элементу:

$('#select3').select3();

Работа с Select2

Select2 популярный плагин, который подключен в GoCore, его документация находится тут.

Дата и время:


Для манипуляций с датой и времинем в GoCore испольщуется плагин flatpickr, его документацию можно посмотреть тут.

Также, используется библиотека moment.js как на сервере, так и на клиенте, документация тут.

Дни недели:


Для выбора дней недели в GoCore испольщуется внутренний плагин daysweekpicker, инициируется на любой элемент,

$('#selector').daysweekpicker();

Чекбоксы:


Чекбоксы в GoCore работают на внутреннем плагине checkboxit, инициируется на чекбокс элемент,

$('input[type="checkbox"]').checkboxIt();

Выбор цвета:


Для выбора цвета в GoCore работает плагин bootstrap-colorpicker.js, инициируется на любой элемент.

$('#selector').colorpicker();

Проценты:


Для отображения процентов в GoCore работает втроенный плагин, работает только в режиме readonly.

WYSIWYG:


Wysiwyg в GoCore работает с помощью плагина tinymce.

Textarea:


Textarea выводится как есть.

Выбор иконки:


МАТВЕЙ

Работа со списками:


Частым явлением при разработки ERP систем является присвоение связи один ко многим, для этого в GoCore предусмотрен специальный плагин.

/public/assets/js/plugins/two_columns_editor/two_columns_editor.js

Чтобы встроить его в ваш интерфейс, вставьте следующий код:

let tceWrapper = $('#wrapper'); tceWrapper.tce({ parent_id: formInstance.activeId, parent_key: 'organization_id', left_pk: 'type_for_organization_id', right_pk: 'id', left_id: 'id', right_id: 'id', define_id: 'type_for_organization_id', left_name: 'name', right_name: 'type_for_organization', get_left: 'type_for_organization', exclude_left_field: 'type_for_organization_id', command_right: 'get', get_right: 'organization_relation_type_for_organization', get_right_params:[ { key: 'organization_id', value: formInstance.activeId } ], lu_command: 'organization_relation_type_for_organization', add_params: [ { key: 'type_for_organization_id', value: 'GET_ROW_ID' }, { key: 'organization_id', value: formInstance.activeId } ], left_label: 'Все роли', right_label: 'Выбранные роли', search_label: 'Поиск среди ролей', back_button: false });

2 строка: Объявление контейнера.

4 строка: Инициализация плагина на контейнер.

5 строка: parent_id - id родительской сущности.

6 строка: parent_key - Родительский ключ.

7 строка: left_pk - Название поля, являющегося первичным ключом для левого списка.

8 строка: right_pk - Название поля, являющегося первичным ключом для правого списка.

9 строка: left_id - Название поля, являющегося id для левого списка.

10 строка: right_id - Название поля, являющегося id для правого списка.

11 строка: define_id - МАТВЕЙ ЧЕТО Я НЕ ВЫВОЖУ СВОЙ ПЛАГИН, ТЫ ИХ ДЕЛАЛ, МОЖЕШЬ ДОПИСАТЬ?

12 строка: left_name

13 строка: right_name

14 строка: get_left

15 строка: exclude_left_field

16 строка: command_right

17 строка: get_right

18 строка: get_right_params

20 строка: key

21 строка: value

24 строка: lu_command

25 строка: add_params

27 строка: key

28 строка: value

35 строка: left_label

36 строка: right_label

37 строка: search_label

38 строка: back_button

Бэкенд:

Базовые модули бэкенд.



Роллбэки

ВАНЯ

Кеширование

ВАНЯ

Блокировки

ВАНЯ

Пользователи, роли и доступы:

Создание пользователя


Меню: Access -> Users

Пользователя можно создать в таблице или в форме.

Обязательные поля:

  1. firstname: Имя пользователя
  2. midname: Отчество пользователя
  3. lastname: Фамилия пользователя
  4. email / login: Email пользователя, оно же служит логином.
  5. Статус: Статус пользователя, по умолчанию устанавливается "Ожидает активации", после сохранения нового пользователя необходимо установить статус "Активный" и сохранить.
  6. Тип пользователя: Для обычных пользователей устанавливается "User".
    Для пользователей типа РОЛЬ - устанавливается "Role".
    Для внешних пользователей, например ресурсов так или иначе взаимодействующих по API - устанавливается "Site".
    Для администраторов системы устанавливается "Admin".
  7. Пароль: Укажите пароль.

Управление пользователями


Меню: Access -> Users

Управление пользователями доступно через таблицу пользователей или через форму конкретного пользвателя.

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

Форма пользователя, которая открывается из таблицы пользователей является администраторской, в ней доступно больше полей.

Смена пароля


Смена пароля производится через форму пользователя или при нажатии на выход при зажатой клавише CTRL.


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


Администратор системы может устанавливать пароль вручную через таблицу пользователей в Access -> Users

Назначение ролей


Для назначения ролей пользователю необходимо кликнуть правой клавишей по пользователю в таблице пользователей и выбрать пункт "Назначить роль / Configure roles".


В открывшемся интерфейсе можно присвоить пользователю роли или отключить подключенные.

Доступ по списку


ВАНЯ

Роли

Создание роли


Роль в GoCore работает на базе класса User, просто отмечается типом "Role".

Для создания роли необходимо зайти в Access -> Roles и создать роль через таблицу или форму, также как это делается для создания пользователя, однако, заполнять необходимо только поле "firstname", на английскими заглавными буквами и установить тип пользователя "Role", остальные поля заполнять не нужно.

Настройка роли


Для настройки роли, назначения команд к которым будет у роли будет доступ и к которым не будет.

Для настройки роли необходимо кликнуть правой клавишей по роли в таблице ролей и выбрать пункт "Configure access".


В открывшемся интерфейсе, слева будет доступно дерево классов, их методов и операций.
Справа - управление доступом в выбранному методу / операции.

  1. Disallow all - Запретить доступ к методу / операции.
  2. Allow access - Выдать доступ к методу / операции.
  3. Access by list - Выдать доступ по списку к методу / операции. ВАНЯ

Client objects - Доступ к клиентским объектам -ВАНЯ


  1. Allow all - Выдать доступ для клиентских объектов. ВАНЯ
  2. Disallow all - Запретить доступ для клиентских объектов. ВАНЯ

Базовые доступы


ВАНЯ

Динамические поля:

ВАНЯ


Отчеты

Конфигурация


САНЯ ВАНЯ

Выгрузка таблиц


САНЯ ВАНЯ

Создание отчета в .DOC


САНЯ ВАНЯ

Создание отчета в .XLSX


САНЯ ВАНЯ

Готовые модули

Чат



Структура

МАТВЕЙ

Классы

МАТВЕЙ

Подключение

МАТВЕЙ

Настройки

МАТВЕЙ

Видеосвязь

Структура

ИСА

Классы

ИСА

Подключение

ИСА

Настройки

ИСА

Миграция из внешних систем

Подготовка окружения


ВАНЯ

Конфигурация


ВАНЯ

Интеграция по API


ВАНЯ

Диплоймент

Настройки


ВАНЯ

Диплоймент


ВАНЯ

GoCore для создания сайта.

Введение


В GoCore предусмотрена специальная, отдельная версия для разработки сайта, который будет напрямую подключен к основной ERP системе, что позволяет удобно и безопасно взаимодействовать с данными системы.

Зависимости - ДОПИСАТЬ


Версия GoCore для Сайта (Далее GoCore-site) устанавливается также как и обычная версия GoCore, помимо nodeJs, mariaDB и прочего, должна быть развернута и запущена основная версия GoCore.

Скачивание - ДОПИСАТЬ


  Скачать GoCore site
  1. Откройте проект в вашей среде разработки.
  2. Установите node modules, выполнив команду "npm i" через терминал. (Если вы только что установили nodeJs, терминал может не знать команду npm, нужно перезагрузить компьютер)

База данных - ДОПИСАТЬ


  1. Откройте navicat или другую программу для управления базами данных.
  2. Создайте новое подключение к MariaDB.

    Connection name: localhost

    User name: root

    Password: Пароль, который вы указали при установке mariaDB

  3. В созданном подключении создайте новую базу данных.

    Database name: Придумайте название вашей базы данных, оно же должно быть прописано в конфиге GoCore (config/config.json), в mysqlConnection - database

    Character set: utf8

    Collation: utf8_general_ci

  4. Залить дамп в созданную базу (execute sql file), сам дамп лежит в GoCore, в папке DB, файл .sql

Среда разработки - ДОПИСАТЬ


Вы можете использовать вашу любимую среду разработки, мы пользуемся PhpStorm/WebStorm и другими продуктами JetBrains.

  1. Откройте проект в вашей среде разработки.
  2. Зайдите в /config/config_example.json и создайте его копию, назовите config.json
  3. В созданном файле config.json укажите:

    Название базы данных (mysqlConnection -> database) : Название вашей базы данных

    Пароль к базе данных (mysqlConnection -> password) : Пароль от вашей базы данных

  4. Настройте конфигурацию запуска проекта:

    Создайте новый конфиг для NodeJs.

    Название: DEV

    NodeJs interpreter: Укажите путь к nodejs.exe

    В качестве запускаемого javascript file укажите путь к файлу: /bin/www.js

    Application parameter: config.json

    Сохраните конфигурацию.

  5. Запустите проект.
  6. Зайдите на localhost:8080 и авторизуйтесь в системе

    Логин: admin@go-core.ru

    Пароль: welcomebro

Обзор директорий


Роутинг


Общение с системой


Нюансы