apress-documentation 0.4.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +7 -0
- data/.drone.yml +28 -0
- data/.gitignore +10 -0
- data/Appraisals +30 -0
- data/CHANGELOG.md +34 -0
- data/Gemfile +4 -0
- data/README.md +101 -0
- data/Rakefile +6 -0
- data/app/assets/javascripts/package/documentation.js +18 -0
- data/app/assets/javascripts/shared/dependency_switcher.js +10 -0
- data/app/assets/javascripts/swagger_binder.js +19 -0
- data/app/assets/javascripts/swagger_ui.js +24 -0
- data/app/assets/javascripts/templates/document.hamlbars +25 -0
- data/app/assets/stylesheets/document/base.scss +112 -0
- data/app/assets/stylesheets/document/document.scss +19 -0
- data/app/assets/stylesheets/document/layout.scss +9 -0
- data/app/assets/stylesheets/document/sidebar.scss +19 -0
- data/app/assets/stylesheets/document/swagger.scss +3 -0
- data/app/assets/stylesheets/document/switch.scss +46 -0
- data/app/assets/stylesheets/document/variables.scss +26 -0
- data/app/assets/stylesheets/package/documentation.css +9 -0
- data/app/assets/stylesheets/package/swagger_print.css +4 -0
- data/app/assets/stylesheets/package/swagger_screen.css +4 -0
- data/app/controllers/apress/documentation/documents_controller.rb +14 -0
- data/app/controllers/apress/documentation/swagger_controller.rb +22 -0
- data/app/controllers/apress/documentation/swagger_ui_controller.rb +11 -0
- data/app/controllers/concerns/apress/documentation/preload_docs.rb +20 -0
- data/app/helpers/apress/documentation/documents_helper.rb +14 -0
- data/app/presenters/apress/documentation/dependency_presenter.rb +75 -0
- data/app/services/apress/documentation/swagger_json_builder.rb +22 -0
- data/app/views/apress/documentation/documents/_document.html.haml +32 -0
- data/app/views/apress/documentation/documents/_swagger.html.haml +10 -0
- data/app/views/apress/documentation/documents/show.html.haml +13 -0
- data/app/views/apress/documentation/presenters/dependency_presenter/_dependencies.html.haml +21 -0
- data/app/views/apress/documentation/presenters/dependency_presenter/_links.html.haml +17 -0
- data/app/views/apress/documentation/swagger_ui/show.html.haml +26 -0
- data/app/views/layouts/apress/documentation/_menu.html.haml +6 -0
- data/app/views/layouts/apress/documentation/_menu_item.html.haml +7 -0
- data/app/views/layouts/apress/documentation/_sidebar.html.haml +2 -0
- data/app/views/layouts/documentation.html.haml +17 -0
- data/apress-documentation.gemspec +35 -0
- data/config/routes.rb +16 -0
- data/dip.yml +48 -0
- data/docker-compose.development.yml +18 -0
- data/docker-compose.drone.yml +7 -0
- data/docker-compose.yml +10 -0
- data/lib/apress/documentation.rb +48 -0
- data/lib/apress/documentation/dsl/compilers/base_compiler.rb +32 -0
- data/lib/apress/documentation/dsl/compilers/document_compiler.rb +111 -0
- data/lib/apress/documentation/dsl/compilers/mixins/dependable.rb +31 -0
- data/lib/apress/documentation/dsl/compilers/mixins/publicity.rb +34 -0
- data/lib/apress/documentation/dsl/compilers/swagger_compiler.rb +25 -0
- data/lib/apress/documentation/dsl/document.rb +14 -0
- data/lib/apress/documentation/dsl/modules.rb +40 -0
- data/lib/apress/documentation/dsl/swagger_document.rb +14 -0
- data/lib/apress/documentation/dsl/utils/swagger_bind_point_extractor.rb +37 -0
- data/lib/apress/documentation/engine.rb +16 -0
- data/lib/apress/documentation/extensions/rgl/adjacency.rb +18 -0
- data/lib/apress/documentation/storage/base_storage.rb +88 -0
- data/lib/apress/documentation/storage/dependency_graph.rb +96 -0
- data/lib/apress/documentation/storage/document.rb +52 -0
- data/lib/apress/documentation/storage/modules.rb +83 -0
- data/lib/apress/documentation/storage/swagger_document.rb +62 -0
- data/lib/apress/documentation/swagger/schema.rb +39 -0
- data/lib/apress/documentation/version.rb +5 -0
- data/spec/app/controllers/documents_controller_spec.rb +42 -0
- data/spec/app/controllers/swagger_controller_spec.rb +46 -0
- data/spec/app/controllers/swagger_ui_controller_spec.rb +11 -0
- data/spec/app/services/swagger_json_builder_spec.rb +41 -0
- data/spec/apress/documentation_spec.rb +342 -0
- data/spec/helpers/apress/documentation/documents_helper_spec.rb +17 -0
- data/spec/internal/app/docs/swagger/root.rb +7 -0
- data/spec/internal/config/database.yml +7 -0
- data/spec/internal/config/environments/test.rb +1 -0
- data/spec/internal/config/hosts.rb +1 -0
- data/spec/internal/config/routes.rb +3 -0
- data/spec/internal/lib/stub_docs/module.rb +3 -0
- data/spec/internal/lib/stub_docs/module/document/child_document.rb +7 -0
- data/spec/internal/log/.gitignore +1 -0
- data/spec/presenters/apress/documentation/dependency_presenter_spec.rb +139 -0
- data/spec/spec_helper.rb +27 -0
- metadata +335 -0
@@ -0,0 +1,14 @@
|
|
1
|
+
require_relative 'compilers/document_compiler'
|
2
|
+
|
3
|
+
module Apress
|
4
|
+
module Documentation
|
5
|
+
module Dsl
|
6
|
+
module Document
|
7
|
+
# Public: Подключает DSL в класс данных документа
|
8
|
+
def compile(fields = {}, &block)
|
9
|
+
Apress::Documentation::Dsl::Compilers::DocumentCompiler.new(self).compile(fields, &block)
|
10
|
+
end
|
11
|
+
end
|
12
|
+
end
|
13
|
+
end
|
14
|
+
end
|
@@ -0,0 +1,40 @@
|
|
1
|
+
module Apress
|
2
|
+
module Documentation
|
3
|
+
module Dsl
|
4
|
+
module Modules
|
5
|
+
# Protected: Точка входа для построения DS
|
6
|
+
# используется через делегацию в модуле Apress::Documentation
|
7
|
+
#
|
8
|
+
#
|
9
|
+
# module_slug - Symbol - слаг модуля
|
10
|
+
# fields - Hash(optional, default - {}) - поля для установки в короткой записи
|
11
|
+
# (например, Apress::Documentation.build(:slug, title: 'name'))
|
12
|
+
# &block - Proc(optional) - вызовы DSL методов
|
13
|
+
#
|
14
|
+
# Examples
|
15
|
+
#
|
16
|
+
# Apress::Documentation.build(:module) do
|
17
|
+
# name 'some module'
|
18
|
+
# description 'tests'
|
19
|
+
# end
|
20
|
+
#
|
21
|
+
# Apress::Documentation.build(:module) do
|
22
|
+
# document(:some, title: 'Some doc') do
|
23
|
+
# description 'Тут вставить описание'
|
24
|
+
# publicity 'Публичное'
|
25
|
+
# end
|
26
|
+
# end
|
27
|
+
#
|
28
|
+
def build(module_slug, fields = {}, &block)
|
29
|
+
module_slug = module_slug.to_s
|
30
|
+
document = self[module_slug]
|
31
|
+
document ||= Apress::Documentation::Storage::Document.new(module_slug)
|
32
|
+
Apress::Documentation::Storage::DependencyGraph.instance.add_document(document)
|
33
|
+
self << document
|
34
|
+
|
35
|
+
document.compile(fields, &block)
|
36
|
+
end
|
37
|
+
end
|
38
|
+
end
|
39
|
+
end
|
40
|
+
end
|
@@ -0,0 +1,14 @@
|
|
1
|
+
require_relative 'compilers/swagger_compiler'
|
2
|
+
|
3
|
+
module Apress
|
4
|
+
module Documentation
|
5
|
+
module Dsl
|
6
|
+
module SwaggerDocument
|
7
|
+
# Public: Подключает DSL в класс данных swagger-описания
|
8
|
+
def compile(fields = {}, &block)
|
9
|
+
Apress::Documentation::Dsl::Compilers::SwaggerCompiler.new(self).compile(fields, &block)
|
10
|
+
end
|
11
|
+
end
|
12
|
+
end
|
13
|
+
end
|
14
|
+
end
|
@@ -0,0 +1,37 @@
|
|
1
|
+
module Apress
|
2
|
+
module Documentation
|
3
|
+
module Dsl
|
4
|
+
module Utils
|
5
|
+
# Private: "Распознает" идентификатор html-tag'а в SwaggerUI по переданному блоку Swagger::Blocks,
|
6
|
+
# в который будет вставлена дополнительная информация из SwaggerDocument.
|
7
|
+
#
|
8
|
+
# Идея: Выполнить блок DSL swagger_path из Swagger::Blocks без вызовов реальных методов.
|
9
|
+
#
|
10
|
+
# Алгоритм:
|
11
|
+
# - Выполняем переданный блок от swagger_path, пропуская неизвестные методы
|
12
|
+
# - как только нашли первый вызов "key :operationId, value", запоминаем value
|
13
|
+
# - тоже самое для key :tags, [value]
|
14
|
+
# - если после выполнения блока оба значения заданы (@tag, @operation_id) возвращаем результат
|
15
|
+
class SwaggerBindPointExtractor
|
16
|
+
def extract(&block)
|
17
|
+
instance_eval(&block)
|
18
|
+
"#{@tag}_#{@operation_id}" if @tag && @operation_id
|
19
|
+
end
|
20
|
+
|
21
|
+
def method_missing(name, *args, &block)
|
22
|
+
if block_given?
|
23
|
+
instance_eval(&block)
|
24
|
+
elsif name.to_s == 'key'
|
25
|
+
case args[0]
|
26
|
+
when :operationId
|
27
|
+
@operation_id ||= args[1]
|
28
|
+
when :tags
|
29
|
+
@tag ||= args[1].try(:first)
|
30
|
+
end
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
36
|
+
end
|
37
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
module Apress
|
2
|
+
module Documentation
|
3
|
+
class Engine < Rails::Engine
|
4
|
+
config.autoload_paths += [
|
5
|
+
config.root.join('app', 'controllers', 'concerns'),
|
6
|
+
config.root.join('app', 'presenters')
|
7
|
+
]
|
8
|
+
|
9
|
+
config.documentation = {path_scope: nil, routes_constraints: {domain: :current}}
|
10
|
+
|
11
|
+
initializer "apress-documentation", before: :load_init_rb do |app|
|
12
|
+
RGL::DirectedAdjacencyGraph.include Apress::Documentation::Extensions::RGL::Adjacency
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
@@ -0,0 +1,18 @@
|
|
1
|
+
module Apress
|
2
|
+
module Documentation
|
3
|
+
module Extensions
|
4
|
+
module RGL
|
5
|
+
module Adjacency
|
6
|
+
# Private: Расширение графа для замены вершины на новую
|
7
|
+
def replace_vertex(old_v, new_v)
|
8
|
+
@vertices_dict[new_v] = @vertices_dict.delete(old_v)
|
9
|
+
|
10
|
+
@vertices_dict.each_value do |list|
|
11
|
+
list.add(new_v) if list.delete?(old_v)
|
12
|
+
end
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
17
|
+
end
|
18
|
+
end
|
@@ -0,0 +1,88 @@
|
|
1
|
+
module Apress
|
2
|
+
module Documentation
|
3
|
+
module Storage
|
4
|
+
# Private: AbstractClass, Базовый класс хранилища
|
5
|
+
#
|
6
|
+
# описывает методы аттрибутов для сериализации в json формата:
|
7
|
+
# {
|
8
|
+
# {
|
9
|
+
# "attr_0": send(:attr_0),
|
10
|
+
# "attr_1": send(:attr_1),
|
11
|
+
# ....
|
12
|
+
# }
|
13
|
+
# }
|
14
|
+
class BaseStorage
|
15
|
+
# Public: Составной слаг, используется как URL
|
16
|
+
attr_reader :slug
|
17
|
+
|
18
|
+
def self.json_attr_names
|
19
|
+
@json_attr_names ||= []
|
20
|
+
end
|
21
|
+
|
22
|
+
# Public: Задает аттрибуты для сериализации в json
|
23
|
+
def self.json_attr(*method_names)
|
24
|
+
json_attr_names.concat(method_names.map(&:to_s))
|
25
|
+
|
26
|
+
attr_accessor(*method_names)
|
27
|
+
end
|
28
|
+
|
29
|
+
# Public: Сериализует объект в JSON
|
30
|
+
def as_json(options = {})
|
31
|
+
self.class.json_attr_names.each_with_object({}) do |attr_name, json|
|
32
|
+
value = send(attr_name)
|
33
|
+
|
34
|
+
json[attr_name] = value if value
|
35
|
+
end
|
36
|
+
end
|
37
|
+
|
38
|
+
# Public: задает аттрибуты на основе хеша
|
39
|
+
def assign(options = {})
|
40
|
+
options.each do |key, value|
|
41
|
+
unless self.class.json_attr_names.include?(key.to_s)
|
42
|
+
raise "Undefined attribute #{key}, allowed attributes are #{self.class.json_attr_names}"
|
43
|
+
end
|
44
|
+
|
45
|
+
send("#{key}=", value)
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
49
|
+
def eql?(other)
|
50
|
+
slug == other.to_s
|
51
|
+
end
|
52
|
+
alias_method :==, :eql?
|
53
|
+
|
54
|
+
def to_s
|
55
|
+
slug.to_s
|
56
|
+
end
|
57
|
+
|
58
|
+
def hash
|
59
|
+
slug.hash
|
60
|
+
end
|
61
|
+
|
62
|
+
def inspect
|
63
|
+
"<#{self.class} slug = #{slug}>"
|
64
|
+
end
|
65
|
+
|
66
|
+
# Public: находит зависимости для текущего документа
|
67
|
+
#
|
68
|
+
# Arguments:
|
69
|
+
# reverse - флаг для отпеределения какой тип зависимостей нужно вернуть
|
70
|
+
# возможные значения
|
71
|
+
# - false (default) - документы, от которых зависит текущий документ (AKA зависимости self)
|
72
|
+
# - true - документы, которые зависят от текущего (AKA потребители self)
|
73
|
+
#
|
74
|
+
# Returns Array of Pairs - [[doc1, doc2], [doc1, doc2]]
|
75
|
+
def dependencies(reverse: false)
|
76
|
+
@dependencies ||= Hash.new do |hash, key|
|
77
|
+
hash[key] = Storage::DependencyGraph.instance.dependencies(
|
78
|
+
self,
|
79
|
+
reverse: key
|
80
|
+
)
|
81
|
+
end
|
82
|
+
|
83
|
+
@dependencies[reverse]
|
84
|
+
end
|
85
|
+
end
|
86
|
+
end
|
87
|
+
end
|
88
|
+
end
|
@@ -0,0 +1,96 @@
|
|
1
|
+
require 'singleton'
|
2
|
+
|
3
|
+
module Apress
|
4
|
+
module Documentation
|
5
|
+
module Storage
|
6
|
+
# Private: Основное хранилище всех зависимостей между документами
|
7
|
+
# Инкапсулирует орентированный граф, вершины которого документы (Document или SwaggerDocument)
|
8
|
+
class DependencyGraph
|
9
|
+
include Singleton
|
10
|
+
|
11
|
+
# Public: добавление документа
|
12
|
+
#
|
13
|
+
# Arguments:
|
14
|
+
# document - (String or Document) - документ или его слаг(если документ еще не был создан)
|
15
|
+
#
|
16
|
+
# Note:
|
17
|
+
# Данный метод позволяет ""лениво"" создавать документы в графе,
|
18
|
+
# подменяя слаг документа, вставленного в граф до создания самого документа, на сам документ
|
19
|
+
# Returns nothing
|
20
|
+
def add_document(document)
|
21
|
+
if graph.has_vertex?(document)
|
22
|
+
graph.replace_vertex(document, document)
|
23
|
+
else
|
24
|
+
graph.add_vertex(document)
|
25
|
+
end
|
26
|
+
end
|
27
|
+
|
28
|
+
# Public: добавление связи между документами, создает ребро в графе, если оно не было создано
|
29
|
+
#
|
30
|
+
# Arguments:
|
31
|
+
# document_from - (Document) - документ от который зависит
|
32
|
+
# document_to - (String or Document) - документ или его слаг(если документ еще не был создан)
|
33
|
+
#
|
34
|
+
# Returns nothing
|
35
|
+
def add_dependency(document_from, document_to)
|
36
|
+
graph.add_edge(document_from, document_to) unless graph.has_edge?(document_from, document_to)
|
37
|
+
end
|
38
|
+
|
39
|
+
# Public: находит все зависимости для заданного документа
|
40
|
+
#
|
41
|
+
# Arguments:
|
42
|
+
# contract - (Document) - документ для которого определяем зависимости
|
43
|
+
# reverse - (boolean) - флаг, различает тип определяемых зависимостей
|
44
|
+
# возможные значения
|
45
|
+
# - false (default) - документы, от которых зависит текущий документ (AKA зависимости contract)
|
46
|
+
# - true - документы, которые зависят от текущего (AKA потребители contract)
|
47
|
+
#
|
48
|
+
# Returns Array of Pairs - [[doc_from, doc_to], [doc_from_other, doc_to_other]]
|
49
|
+
def dependencies(contract, reverse:)
|
50
|
+
dep = []
|
51
|
+
|
52
|
+
condition =
|
53
|
+
if reverse
|
54
|
+
lambda { |doc, _, to| doc == to }
|
55
|
+
else
|
56
|
+
lambda { |doc, from, _| doc == from }
|
57
|
+
end
|
58
|
+
|
59
|
+
graph.each_edge do |from, to|
|
60
|
+
next unless condition.call(contract, from, to)
|
61
|
+
|
62
|
+
dep << (reverse ? [to, from] : [from, to])
|
63
|
+
end
|
64
|
+
|
65
|
+
dep
|
66
|
+
end
|
67
|
+
|
68
|
+
# Public: валидирует зависимости
|
69
|
+
#
|
70
|
+
# Throws RuntimeError если найдена вершина неверного типа
|
71
|
+
#
|
72
|
+
# Returns nothing
|
73
|
+
def validate!
|
74
|
+
graph.each_vertex do |v|
|
75
|
+
unless v.is_a?(Apress::Documentation::Storage::BaseStorage)
|
76
|
+
raise "Несуществующий документ - #{v}, объявлен в - #{dependencies(v, reverse: true).map(&:last)}"
|
77
|
+
end
|
78
|
+
end
|
79
|
+
end
|
80
|
+
|
81
|
+
# Public: очищает все текущие зависисмости
|
82
|
+
#
|
83
|
+
# Returns nothing
|
84
|
+
def reset!
|
85
|
+
@graph = RGL::DirectedAdjacencyGraph.new
|
86
|
+
end
|
87
|
+
|
88
|
+
private
|
89
|
+
|
90
|
+
def graph
|
91
|
+
@graph ||= RGL::DirectedAdjacencyGraph.new
|
92
|
+
end
|
93
|
+
end
|
94
|
+
end
|
95
|
+
end
|
96
|
+
end
|
@@ -0,0 +1,52 @@
|
|
1
|
+
require_relative 'base_storage'
|
2
|
+
require_relative '../dsl/document'
|
3
|
+
|
4
|
+
module Apress
|
5
|
+
module Documentation
|
6
|
+
module Storage
|
7
|
+
# Protected
|
8
|
+
#
|
9
|
+
# Внутренний класс системы документации
|
10
|
+
# Описывает отдельный документ
|
11
|
+
class Document < BaseStorage
|
12
|
+
include Apress::Documentation::Dsl::Document
|
13
|
+
# Public: Заголовок документа
|
14
|
+
json_attr :title
|
15
|
+
# Public: Описание документа
|
16
|
+
json_attr :description
|
17
|
+
# Public: Бизнесс описание - заполняется менаджером
|
18
|
+
json_attr :business_desc
|
19
|
+
# Public: Наличие тестов, ссылка на задачу с тестами
|
20
|
+
json_attr :tests
|
21
|
+
# Public: Публичность описываемого функционала - (Защищенный, Публичный)
|
22
|
+
json_attr :publicity
|
23
|
+
|
24
|
+
def initialize(slug)
|
25
|
+
@slug = slug
|
26
|
+
end
|
27
|
+
|
28
|
+
# Public: проверка, необходимо ли для данного документа отображать SwaggerUI
|
29
|
+
def swagger?
|
30
|
+
!swagger_documents.empty?
|
31
|
+
end
|
32
|
+
|
33
|
+
# Public: Хранит дочерние документы
|
34
|
+
def documents
|
35
|
+
@documents ||= {}
|
36
|
+
end
|
37
|
+
|
38
|
+
# Public: Хранит объекты SwaggerDocument для отображения на одной старнице через SwaggerUI
|
39
|
+
def swagger_documents
|
40
|
+
@swagger_documents ||= {}
|
41
|
+
end
|
42
|
+
|
43
|
+
# Public: находит документ верхнего уровня - модуль
|
44
|
+
#
|
45
|
+
# Returns Document
|
46
|
+
def current_module
|
47
|
+
Apress::Documentation::Storage::Modules.instance[slug.to_s.split('/').first]
|
48
|
+
end
|
49
|
+
end
|
50
|
+
end
|
51
|
+
end
|
52
|
+
end
|
@@ -0,0 +1,83 @@
|
|
1
|
+
require 'singleton'
|
2
|
+
require_relative '../dsl/modules'
|
3
|
+
|
4
|
+
module Apress
|
5
|
+
module Documentation
|
6
|
+
module Storage
|
7
|
+
# Protected
|
8
|
+
#
|
9
|
+
# Класс хранения документов верхнего уровня (модулей)
|
10
|
+
class Modules
|
11
|
+
include Apress::Documentation::Dsl::Modules
|
12
|
+
include Singleton
|
13
|
+
|
14
|
+
# Public
|
15
|
+
#
|
16
|
+
# Хеш модулей
|
17
|
+
def data
|
18
|
+
@data ||= {}
|
19
|
+
end
|
20
|
+
|
21
|
+
# Public
|
22
|
+
#
|
23
|
+
# Добавление модуля
|
24
|
+
#
|
25
|
+
# Arguments
|
26
|
+
# document - Document
|
27
|
+
#
|
28
|
+
# Example usage:
|
29
|
+
# Apress::Documentation::Modules.instance << document
|
30
|
+
def <<(document)
|
31
|
+
data[document.slug.to_s] = document
|
32
|
+
end
|
33
|
+
|
34
|
+
# Public
|
35
|
+
#
|
36
|
+
# Поиск модуля
|
37
|
+
#
|
38
|
+
# Arguments
|
39
|
+
# slug - String (или любой совместимый объект) - слаг документа
|
40
|
+
#
|
41
|
+
# Example usage:
|
42
|
+
# Apress::Documentation::Modules.instance[slug]
|
43
|
+
#
|
44
|
+
# Returns Document
|
45
|
+
def [](slug)
|
46
|
+
data[slug.to_s]
|
47
|
+
end
|
48
|
+
|
49
|
+
# Public
|
50
|
+
#
|
51
|
+
# Получение документа по его URL
|
52
|
+
#
|
53
|
+
# Arguments
|
54
|
+
# path - String - строка разделенная '/' (пример "/module/document/some_function")
|
55
|
+
#
|
56
|
+
# Example usage:
|
57
|
+
# Apress::Documentation.fetch_document('module_name/document/test')
|
58
|
+
def fetch_document(path)
|
59
|
+
keys = path.split('/')
|
60
|
+
doc = data[keys.shift]
|
61
|
+
return unless doc
|
62
|
+
|
63
|
+
keys.each do |key|
|
64
|
+
doc = doc.documents[key] || (doc.respond_to?(:swagger_documents) && doc.swagger_documents[key])
|
65
|
+
break unless doc
|
66
|
+
end
|
67
|
+
|
68
|
+
doc
|
69
|
+
end
|
70
|
+
|
71
|
+
# Public
|
72
|
+
#
|
73
|
+
# Удаление всех документов, используется для тестирования
|
74
|
+
#
|
75
|
+
# Example usage:
|
76
|
+
# Apress::Documentation.reset!
|
77
|
+
def reset!
|
78
|
+
@data = {}
|
79
|
+
end
|
80
|
+
end
|
81
|
+
end
|
82
|
+
end
|
83
|
+
end
|