Class: Utopia::Project::Base

Inherits:
Object
  • Object
show all
Extended by:
Thread::Local
Defined in:
lib/utopia/project/base.rb

Overview

Provides structured access to a project directory which contains source code and guides.

Instance Attribute Summary collapse

Class Method Summary collapse

Instance Method Summary collapse

Constructor Details

#initialize(root = Dir.pwd) ⇒ Base

Initialize the project with the given root path.



55
56
57
58
59
60
61
62
63
# File 'lib/utopia/project/base.rb', line 55

def initialize(root = Dir.pwd)
	@root = root
	
	@source_path = Utopia::Path["/source"]
	
	@index = Decode::Index.new
	
	@links = Utopia::Content::Links.new(@root)
end

Instance Attribute Details

#indexObject

The source code index which is used for generating pages.



71
72
73
# File 'lib/utopia/project/base.rb', line 71

def index
  @index
end

#rootObject (readonly)

The file-system path to the root of the project.



67
68
69
# File 'lib/utopia/project/base.rb', line 67

def root
  @root
end

Class Method Details

.localObject



41
42
43
44
45
46
47
48
49
50
51
# File 'lib/utopia/project/base.rb', line 41

def self.local
	instance = self.new
	
	source_files = Dir.glob(
		File.expand_path("lib/**/*.rb", instance.root)
	)
	
	instance.update(source_files)
	
	return instance
end

Instance Method Details

#best(definitions) ⇒ Object

Given an array of defintions, return the best definition for the purposes of generating documentation.



91
92
93
94
95
96
97
98
99
# File 'lib/utopia/project/base.rb', line 91

def best(definitions)
	definitions.each do |definition|
		if definition.documentation
			return definition
		end
	end
	
	return definitions.first
end

#document(text, definition = nil, language: definition&.language) ⇒ Object

Convert the given markdown text into HTML.

  • Updates source code references (‘identifier`) into links.

  • Uses Kramdown to convert the text into HTML.



133
134
135
136
137
138
139
# File 'lib/utopia/project/base.rb', line 133

def document(text, definition = nil, language: definition&.language)
	text = text&.gsub(/(?<!`){(.*?)}/) do |match|
		linkify($1, definition, language: language)
	end
	
	return Kramdown::Document.new(text, syntax_highlighter: nil)
end

#format(text, definition = nil, language: definition&.language) ⇒ Object

Format the given text in the context of the given definition and language. See #document for details.



112
113
114
115
116
117
118
119
120
121
122
123
124
125
# File 'lib/utopia/project/base.rb', line 112

def format(text, definition = nil, language: definition&.language)
	case text
	when Enumerable
		text = text.to_a.join("\n")
	when nil
		return nil
	end
	
	if document = self.document(text, definition, language: language)
		return Trenni::MarkupString.raw(
			document.to_html
		)
	end
end

#guidesObject

Enumerate over all available guides in order.



193
194
195
196
197
198
199
200
201
202
203
# File 'lib/utopia/project/base.rb', line 193

def guides
	return to_enum(:guides) unless block_given?
	
	@links.index("/guides").each do |link|
		guide_path = File.join(@root, link.path)
		
		next unless File.directory?(guide_path)
		
		yield Guide.new(self, guide_path)
	end
end

#id_for(definition, suffix = nil) ⇒ Object

Compute a unique string which can be used as ‘id` attribute in the HTML output.



168
169
170
171
172
173
174
# File 'lib/utopia/project/base.rb', line 168

def id_for(definition, suffix = nil)
	if suffix
		"#{definition.qualified_name}-#{suffix}"
	else
		definition.qualified_name
	end
end

Compute a link href to the given definition for use within the HTML output.



178
179
180
181
182
183
184
185
186
187
# File 'lib/utopia/project/base.rb', line 178

def link_for(definition)
	path = definition.lexical_path.map{|entry| entry.to_s}
	
	if definition.container?
		return Trenni::Reference.new(@source_path + path + "index")
	else
		name = path.pop
		return Trenni::Reference.new(@source_path + path + "index", fragment: id_for(definition))
	end
end

#linkify(text, definition = nil, language: definition&.language) ⇒ Object

Replace source code references in the given text with HTML anchors.



144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
# File 'lib/utopia/project/base.rb', line 144

def linkify(text, definition = nil, language: definition&.language)
	reference = @index.languages.parse_reference(text, default_language: language)
	
	Trenni::Builder.fragment do |builder|
		if reference and definition = @index.lookup(reference, relative_to: definition)&.first
			builder.inline('a', href: link_for(definition)) do
				builder.inline('code', class: "language-#{definition.language.name}") do
					builder.text definition.qualified_form
				end
			end
		elsif reference
			builder.inline('code', class: "language-#{reference.language.name}") do
				builder.text text
			end
		else
			builder.inline('code') do
				builder.text text
			end
		end
	end
end

#lookup(path) ⇒ Object

Given a lexical path, find the best definition for that path.



103
104
105
106
107
# File 'lib/utopia/project/base.rb', line 103

def lookup(path)
	if node = @index.trie.lookup(path.map(&:to_sym))
		return node, best(node.values)
	end
end

#path_for(file_name) ⇒ Object

Return the absolute path for the given file name, if it exists in the project.



76
77
78
79
80
81
# File 'lib/utopia/project/base.rb', line 76

def path_for(file_name)
	full_path = File.expand_path(file_name, @root)
	if File.exist?(full_path)
		return full_path
	end
end

#update(paths) ⇒ Object

Update the index with the specified paths.



85
86
87
# File 'lib/utopia/project/base.rb', line 85

def update(paths)
	@index.update(paths)
end