rails_map 1.1.1 → 1.3.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.
@@ -1,13 +1,10 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  require 'rails/generators'
4
- require 'rails/generators/migration'
5
4
 
6
5
  module RailsMap
7
6
  module Generators
8
7
  class InstallGenerator < Rails::Generators::Base
9
- include Rails::Generators::Migration
10
-
11
8
  source_root File.expand_path('templates', __dir__)
12
9
 
13
10
  desc "Installs RailsMap with environment-based authentication (use --skip-auth to disable)"
@@ -21,7 +18,7 @@ module RailsMap
21
18
 
22
19
  def add_route_mount
23
20
  unless options[:skip_routes]
24
- route "mount RailsMap::Engine, at: '/api-doc'"
21
+ route "mount RailsMap::Engine, at: '/rails-map'"
25
22
  end
26
23
  end
27
24
 
@@ -31,13 +28,13 @@ module RailsMap
31
28
  if File.exist?(gitignore_path)
32
29
  gitignore_content = File.read(gitignore_path)
33
30
 
34
- unless gitignore_content.include?('doc/api')
31
+ unless gitignore_content.include?('doc/rails-map')
35
32
  append_to_file gitignore_path do
36
- "\n# Ignore generated documentation\n/doc/api\n"
33
+ "\n# Ignore generated documentation\n/doc/rails-map\n"
37
34
  end
38
35
  end
39
36
  else
40
- create_file gitignore_path, "# Ignore generated documentation\n/doc/api\n"
37
+ create_file gitignore_path, "# Ignore generated documentation\n/doc/rails-map\n"
41
38
  end
42
39
  end
43
40
 
@@ -3,45 +3,47 @@
3
3
  RailsMap has been installed!
4
4
 
5
5
  ✓ Configuration file created at:
6
- config/initializers/rails_map.rb
6
+ config/initializers/rails_map.rb
7
7
 
8
8
  <% unless options[:skip_routes] %>
9
9
  ✓ Route mounted in config/routes.rb:
10
- mount RailsMap::Engine, at: '/api-doc'
10
+ mount RailsMap::Engine, at: '/rails-map'
11
11
  <% end %>
12
12
 
13
- ✓ Added /doc/api to .gitignore
13
+ ✓ Added /doc/rails-map to .gitignore
14
14
 
15
15
  <% unless options[:skip_auth] %>
16
16
  Authentication has been ENABLED (default)
17
17
 
18
18
  Next steps:
19
+
19
20
  1. Set environment variables:
20
- export RAILS_MAP_USERNAME=admin
21
- export RAILS_MAP_PASSWORD=your_secure_password
21
+ export RAILS_MAP_USERNAME=admin
22
+ export RAILS_MAP_PASSWORD=your_secure_password
22
23
 
23
24
  Or add to .env file:
24
- RAILS_MAP_USERNAME=admin
25
- RAILS_MAP_PASSWORD=your_secure_password
25
+ RAILS_MAP_USERNAME=admin
26
+ RAILS_MAP_PASSWORD=your_secure_password
26
27
 
27
- 2. Restart your server and visit /api-doc
28
+ 2. Restart your server and visit /rails-map
28
29
  You'll be prompted to login with your credentials
29
30
 
30
31
  To disable authentication, run:
31
- rails destroy rails_map:install
32
- rails g rails_map:install --skip-auth
32
+ rails destroy rails_map:install
33
+ rails g rails_map:install --skip-auth
33
34
  <% else %>
34
35
  Authentication has been DISABLED (--skip-auth flag used)
35
36
 
36
37
  To enable authentication:
38
+
37
39
  1. Set RAILS_MAP_USERNAME and RAILS_MAP_PASSWORD environment variables
38
40
  2. Uncomment authentication in config/initializers/rails_map.rb
39
- <% end %>
41
+ <% end %>
40
42
 
41
43
  Documentation:
42
- Visit http://localhost:3000/api-doc after starting your server
44
+ Visit http://localhost:3000/rails-map after starting your server
43
45
 
44
46
  For more information, see:
45
- https://rails-map.netlify.app
47
+ https://rails-map.netlify.app
46
48
 
47
49
  ===============================================================================
@@ -2,13 +2,13 @@
2
2
 
3
3
  RailsMap.configure do |config|
4
4
  # Application name displayed in the documentation
5
- config.app_name = '<%= Rails.application.class.module_parent_name %>'
5
+ config.app_name = '<%= Rails.application.class.respond_to?(:module_parent_name) ? Rails.application.class.module_parent_name : Rails.application.class.parent_name %>'
6
6
 
7
7
  # Theme color (any valid CSS color)
8
8
  config.theme_color = '#3B82F6'
9
9
 
10
10
  # Output directory for static HTML generation
11
- config.output_dir = Rails.root.join('doc', 'api').to_s
11
+ config.output_dir = Rails.root.join('doc', 'rails-map').to_s
12
12
 
13
13
  # Include timestamp columns (created_at, updated_at) in model documentation
14
14
  config.include_timestamps = true
@@ -1,6 +1,6 @@
1
1
  # frozen_string_literal: true
2
2
 
3
- class CreateRailsMapUsers < ActiveRecord::Migration[7.0]
3
+ class CreateRailsMapUsers < ActiveRecord::Migration[<%= ActiveRecord::Migration.current_version %>]
4
4
  def change
5
5
  create_table :rails_map_users do |t|
6
6
  t.string :username, null: false
@@ -18,15 +18,20 @@ module RailsMap
18
18
 
19
19
  def default_output_dir
20
20
  if defined?(Rails)
21
- Rails.root.join("doc", "api").to_s
21
+ Rails.root.join("doc", "rails-map").to_s
22
22
  else
23
- File.join(Dir.pwd, "doc", "api")
23
+ File.join(Dir.pwd, "doc", "rails-map")
24
24
  end
25
25
  end
26
26
 
27
27
  def default_app_name
28
28
  if defined?(Rails)
29
- Rails.application.class.module_parent_name
29
+ app_class = Rails.application.class
30
+ if app_class.respond_to?(:module_parent_name)
31
+ app_class.module_parent_name
32
+ else
33
+ app_class.parent_name
34
+ end
30
35
  else
31
36
  "Rails Application"
32
37
  end
@@ -42,7 +42,7 @@ module RailsMap
42
42
  if defined?(Rails.root)
43
43
  Dir[Rails.root.join('app/models/**/*.rb')].each do |file|
44
44
  begin
45
- require_dependency file
45
+ require file
46
46
  rescue => e
47
47
  # Ignore errors, file might already be loaded
48
48
  end
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  module RailsMap
4
- VERSION = "1.1.1"
4
+ VERSION = "1.3.0"
5
5
  end
data/rails-map-gem.png ADDED
Binary file
data/release.sh ADDED
@@ -0,0 +1,338 @@
1
+ #!/bin/bash
2
+
3
+ # RailsMap Release Script
4
+ # This script builds, pushes the gem to RubyGems, and cleans up old gem files
5
+
6
+ set -e # Exit on error
7
+
8
+ # Colors for output
9
+ RED='\033[0;31m'
10
+ GREEN='\033[0;32m'
11
+ YELLOW='\033[1;33m'
12
+ BLUE='\033[0;34m'
13
+ NC='\033[0m' # No Color
14
+
15
+ # Function to print colored output
16
+ print_info() {
17
+ echo -e "${BLUE}ℹ ${NC}$1"
18
+ }
19
+
20
+ print_success() {
21
+ echo -e "${GREEN}✓${NC} $1"
22
+ }
23
+
24
+ print_warning() {
25
+ echo -e "${YELLOW}⚠${NC} $1"
26
+ }
27
+
28
+ print_error() {
29
+ echo -e "${RED}✗${NC} $1"
30
+ }
31
+
32
+ # Get the current version from version.rb
33
+ CURRENT_VERSION=$(ruby -r ./lib/rails_map/version.rb -e "puts RailsMap::VERSION")
34
+ GEM_NAME="rails_map"
35
+
36
+ echo ""
37
+ print_info "═══════════════════════════════════════════════════════"
38
+ print_info " RailsMap Release Script"
39
+ print_info "═══════════════════════════════════════════════════════"
40
+ echo ""
41
+
42
+ # Show current version
43
+ print_info "Current version: ${CURRENT_VERSION}"
44
+ echo ""
45
+
46
+ # Ask for new version
47
+ print_warning "Enter the new version number (e.g., 1.2.0, 1.2.1, 2.0.0):"
48
+ read -p "Version: " NEW_VERSION
49
+
50
+ # Validate version format
51
+ if [[ ! $NEW_VERSION =~ ^[0-9]+\.[0-9]+\.[0-9]+$ ]]; then
52
+ print_error "Invalid version format. Please use semantic versioning (e.g., 1.2.0)"
53
+ exit 1
54
+ fi
55
+
56
+ # Check if version is different
57
+ if [ "$NEW_VERSION" == "$CURRENT_VERSION" ]; then
58
+ print_warning "New version is the same as current version"
59
+ read -p "Continue anyway? (y/n) " -n 1 -r
60
+ echo ""
61
+ if [[ ! $REPLY =~ ^[Yy]$ ]]; then
62
+ print_error "Release cancelled"
63
+ exit 1
64
+ fi
65
+ fi
66
+
67
+ # Confirm version change
68
+ echo ""
69
+ print_info "Version change: ${CURRENT_VERSION} → ${NEW_VERSION}"
70
+ read -p "Is this correct? (y/n) " -n 1 -r
71
+ echo ""
72
+ if [[ ! $REPLY =~ ^[Yy]$ ]]; then
73
+ print_error "Release cancelled"
74
+ exit 1
75
+ fi
76
+
77
+ # Update version in version.rb
78
+ print_info "Updating version in lib/rails_map/version.rb..."
79
+ sed -i.bak "s/VERSION = \".*\"/VERSION = \"${NEW_VERSION}\"/" lib/rails_map/version.rb
80
+ rm -f lib/rails_map/version.rb.bak
81
+ print_success "Version updated to ${NEW_VERSION}"
82
+
83
+ # Update version in CHANGELOG.md if it has Unreleased section
84
+ if grep -q "\[Unreleased\]" CHANGELOG.md; then
85
+ print_info "Updating CHANGELOG.md..."
86
+ TODAY=$(date +%Y-%m-%d)
87
+ sed -i.bak "s/\[Unreleased\]/[${NEW_VERSION}] - ${TODAY}/" CHANGELOG.md
88
+ rm -f CHANGELOG.md.bak
89
+ print_success "CHANGELOG.md updated"
90
+ fi
91
+
92
+ # Set VERSION and GEM_FILE for the rest of the script
93
+ VERSION=$NEW_VERSION
94
+ GEM_FILE="${GEM_NAME}-${VERSION}.gem"
95
+
96
+ echo ""
97
+ print_info "Preparing to release version ${VERSION}"
98
+ echo ""
99
+
100
+ # Pre-flight checks
101
+ print_info "Running pre-flight checks..."
102
+
103
+ # Check if version.rb exists
104
+ if [ ! -f "lib/rails_map/version.rb" ]; then
105
+ print_error "lib/rails_map/version.rb not found!"
106
+ exit 1
107
+ fi
108
+
109
+ # Check if gemspec exists
110
+ if [ ! -f "${GEM_NAME}.gemspec" ]; then
111
+ print_error "${GEM_NAME}.gemspec not found!"
112
+ exit 1
113
+ fi
114
+
115
+ # Check if CHANGELOG.md has the current version
116
+ if ! grep -q "\[${VERSION}\]" CHANGELOG.md; then
117
+ print_warning "CHANGELOG.md doesn't contain version ${VERSION}"
118
+ read -p "Continue anyway? (y/n) " -n 1 -r
119
+ echo ""
120
+ if [[ ! $REPLY =~ ^[Yy]$ ]]; then
121
+ print_error "Release cancelled"
122
+ exit 1
123
+ fi
124
+ fi
125
+
126
+ print_success "Pre-flight checks passed"
127
+ echo ""
128
+
129
+ # Step 1: Show current status
130
+ CURRENT_BRANCH=$(git branch --show-current 2>/dev/null || echo "unknown")
131
+ print_info "Current branch: ${CURRENT_BRANCH}"
132
+ print_info "Version to release: ${VERSION}"
133
+ echo ""
134
+
135
+ # Step 2: Check for uncommitted changes
136
+ print_info "Checking git status..."
137
+ if [[ -n $(git status -s 2>/dev/null) ]]; then
138
+ print_warning "You have uncommitted changes:"
139
+ git status -s
140
+ echo ""
141
+
142
+ # Ask if user wants to commit version changes
143
+ print_info "Would you like to commit the version changes?"
144
+ read -p "Commit version changes? (y/n) " -n 1 -r
145
+ echo ""
146
+ if [[ $REPLY =~ ^[Yy]$ ]]; then
147
+ git add lib/rails_map/version.rb
148
+ if grep -q "\[${VERSION}\]" CHANGELOG.md; then
149
+ git add CHANGELOG.md
150
+ fi
151
+ git commit -m "Bump version to ${VERSION}"
152
+ print_success "Version changes committed"
153
+
154
+ read -p "Push to remote? (y/n) " -n 1 -r
155
+ echo ""
156
+ if [[ $REPLY =~ ^[Yy]$ ]]; then
157
+ CURRENT_BRANCH=$(git branch --show-current 2>/dev/null || echo "main")
158
+ if git push origin "$CURRENT_BRANCH" 2>/dev/null; then
159
+ print_success "Changes pushed to remote"
160
+ else
161
+ print_warning "Failed to push (may need to set remote)"
162
+ fi
163
+ fi
164
+ else
165
+ print_warning "Continuing with uncommitted changes"
166
+ fi
167
+ echo ""
168
+ fi
169
+
170
+ # Step 3: Run tests (if available)
171
+ if [ -f "Rakefile" ]; then
172
+ print_info "Running tests..."
173
+ if bundle exec rake spec 2>/dev/null; then
174
+ print_success "Tests passed"
175
+ else
176
+ print_warning "Tests failed or not configured"
177
+ read -p "Continue anyway? (y/n) " -n 1 -r
178
+ echo ""
179
+ if [[ ! $REPLY =~ ^[Yy]$ ]]; then
180
+ print_error "Release cancelled"
181
+ exit 1
182
+ fi
183
+ fi
184
+ echo ""
185
+ fi
186
+
187
+ # Step 4: Delete old gem files
188
+ print_info "Cleaning up old gem files..."
189
+ OLD_GEMS=$(ls ${GEM_NAME}-*.gem 2>/dev/null || true)
190
+ if [ -n "$OLD_GEMS" ]; then
191
+ for gem_file in $OLD_GEMS; do
192
+ rm -f "$gem_file"
193
+ print_success "Deleted: $gem_file"
194
+ done
195
+ else
196
+ print_info "No old gem files found"
197
+ fi
198
+ echo ""
199
+
200
+ # Step 5: Build the gem
201
+ print_info "Building gem: ${GEM_FILE}..."
202
+ echo ""
203
+ if gem build ${GEM_NAME}.gemspec; then
204
+ echo ""
205
+ print_success "Gem built successfully: ${GEM_FILE}"
206
+ else
207
+ echo ""
208
+ print_error "Failed to build gem"
209
+ exit 1
210
+ fi
211
+ echo ""
212
+
213
+ # Step 6: Verify the gem file exists
214
+ if [ ! -f "$GEM_FILE" ]; then
215
+ print_error "Gem file not found: ${GEM_FILE}"
216
+ exit 1
217
+ fi
218
+
219
+ # Step 7: Show gem size
220
+ GEM_SIZE=$(ls -lh "$GEM_FILE" | awk '{print $5}')
221
+ print_info "Gem size: ${GEM_SIZE}"
222
+ echo ""
223
+
224
+ # Step 8: Final confirmation before pushing
225
+ print_warning "═══════════════════════════════════════════════════════"
226
+ print_warning " READY TO PUSH TO RUBYGEMS"
227
+ print_warning "═══════════════════════════════════════════════════════"
228
+ print_info "Gem: ${GEM_NAME}"
229
+ print_info "Version: ${VERSION}"
230
+ print_info "File: ${GEM_FILE}"
231
+ print_info "Size: ${GEM_SIZE}"
232
+ echo ""
233
+ print_warning "This will publish the gem to RubyGems.org"
234
+ read -p "Are you sure you want to continue? (y/n) " -n 1 -r
235
+ echo ""
236
+ if [[ ! $REPLY =~ ^[Yy]$ ]]; then
237
+ print_error "Release cancelled"
238
+ print_info "Gem file ${GEM_FILE} has been built but not pushed"
239
+ print_info "You can manually push it later with: gem push ${GEM_FILE}"
240
+ exit 0
241
+ fi
242
+ echo ""
243
+
244
+ # Step 9: Push to RubyGems
245
+ print_info "Pushing gem to RubyGems..."
246
+ if gem push $GEM_FILE; then
247
+ echo ""
248
+ print_success "Gem pushed successfully to RubyGems!"
249
+ else
250
+ echo ""
251
+ print_error "Failed to push gem to RubyGems"
252
+ print_info "Gem file ${GEM_FILE} is still available locally"
253
+ print_info "You can try pushing manually with: gem push ${GEM_FILE}"
254
+ echo ""
255
+
256
+ # Ask if user wants to rollback version changes
257
+ print_warning "Would you like to rollback the version changes?"
258
+ read -p "Rollback to version ${CURRENT_VERSION}? (y/n) " -n 1 -r
259
+ echo ""
260
+ if [[ $REPLY =~ ^[Yy]$ ]]; then
261
+ # Rollback version.rb
262
+ sed -i.bak "s/VERSION = \".*\"/VERSION = \"${CURRENT_VERSION}\"/" lib/rails_map/version.rb
263
+ rm -f lib/rails_map/version.rb.bak
264
+ print_success "Version rolled back to ${CURRENT_VERSION}"
265
+
266
+ # Rollback CHANGELOG.md if it was updated
267
+ if grep -q "\[${VERSION}\]" CHANGELOG.md; then
268
+ sed -i.bak "s/\[${VERSION}\] - [0-9-]*/[Unreleased]/" CHANGELOG.md
269
+ rm -f CHANGELOG.md.bak
270
+ print_success "CHANGELOG.md rolled back"
271
+ fi
272
+
273
+ # Rollback git commit if it was made
274
+ if git log -1 --pretty=%B 2>/dev/null | grep -q "Bump version to ${VERSION}"; then
275
+ git reset --soft HEAD~1
276
+ print_success "Git commit rolled back"
277
+ fi
278
+ fi
279
+
280
+ exit 1
281
+ fi
282
+ echo ""
283
+
284
+ # Step 10: Create git tag
285
+ TAG_NAME="v${VERSION}"
286
+ print_info "Git tag: ${TAG_NAME}"
287
+ read -p "Create and push git tag? (y/n) " -n 1 -r
288
+ echo ""
289
+ if [[ $REPLY =~ ^[Yy]$ ]]; then
290
+ if git tag -a "$TAG_NAME" -m "Release version ${VERSION}" 2>/dev/null; then
291
+ print_success "Tag created: ${TAG_NAME}"
292
+
293
+ read -p "Push tag to remote? (y/n) " -n 1 -r
294
+ echo ""
295
+ if [[ $REPLY =~ ^[Yy]$ ]]; then
296
+ if git push origin "$TAG_NAME" 2>/dev/null; then
297
+ print_success "Tag pushed to remote"
298
+ else
299
+ print_warning "Failed to push tag (may need to set remote)"
300
+ fi
301
+ fi
302
+ else
303
+ print_warning "Tag already exists or failed to create"
304
+ fi
305
+ echo ""
306
+ fi
307
+
308
+ # Step 11: Clean up gem file
309
+ print_info "Local gem file: ${GEM_FILE}"
310
+ read -p "Delete local gem file? (y/n) " -n 1 -r
311
+ echo ""
312
+ if [[ $REPLY =~ ^[Yy]$ ]]; then
313
+ rm -f "$GEM_FILE"
314
+ print_success "Deleted: ${GEM_FILE}"
315
+ else
316
+ print_info "Keeping: ${GEM_FILE}"
317
+ fi
318
+ echo ""
319
+
320
+ # Step 12: Success summary
321
+ print_success "═══════════════════════════════════════════════════════"
322
+ print_success " RELEASE COMPLETED SUCCESSFULLY! 🎉"
323
+ print_success "═══════════════════════════════════════════════════════"
324
+ echo ""
325
+ print_info "Gem: ${GEM_NAME} v${VERSION}"
326
+ print_info "RubyGems: https://rubygems.org/gems/${GEM_NAME}"
327
+ print_info "Install: gem install ${GEM_NAME}"
328
+ echo ""
329
+ print_info "Next steps:"
330
+ echo " 1. ✓ Gem published to RubyGems"
331
+ echo " 2. ✓ Version updated to ${VERSION}"
332
+ echo " 3. → Verify gem installation: gem install ${GEM_NAME}"
333
+ echo " 4. → Create a GitHub release"
334
+ echo " 5. → Announce the release"
335
+ echo " 6. → Update documentation if needed"
336
+ echo ""
337
+ print_success "Great work! 🚀"
338
+ echo ""
@@ -33,8 +33,7 @@
33
33
  <th>Method</th>
34
34
  <th>Path</th>
35
35
  <th>Action</th>
36
- <th>Route Name</th>
37
- <th>Constraints</th>
36
+ <th>Parameters</th>
38
37
  </tr>
39
38
  </thead>
40
39
  <tbody>
@@ -48,19 +47,41 @@
48
47
  <td><code><%= route.path %></code></td>
49
48
  <td><code><%= route.action %></code></td>
50
49
  <td>
51
- <% if route.name %>
52
- <code><%= route.name %></code>
53
- <% else %>
54
- <span style="color: var(--text-muted);">—</span>
50
+ <% all_params = [] %>
51
+ <% all_params += route.path_params if route.path_params&.any? %>
52
+ <% verb = route.verb.to_s.upcase %>
53
+ <% if %w[GET DELETE].include?(verb) %>
54
+ <% all_params += route.query_params if route.query_params&.any? %>
55
+ <% elsif %w[POST PUT PATCH].include?(verb) %>
56
+ <% all_params += route.request_body_params if route.request_body_params&.any? %>
55
57
  <% end %>
56
- </td>
57
- <td>
58
- <% if route.constraints.any? %>
59
- <% route.constraints.each do |key, value| %>
60
- <code><%= key %>: <%= value %></code><br>
61
- <% end %>
58
+
59
+ <% if all_params.any? %>
60
+ <details style="cursor: pointer;">
61
+ <summary style="color: var(--primary-color); font-weight: 500;">
62
+ <%= all_params.size %> parameter<%= all_params.size > 1 ? 's' : '' %>
63
+ </summary>
64
+ <div style="margin-top: 0.5rem; padding: 0.75rem; background: var(--bg-color); border-radius: 6px; font-size: 0.875rem;">
65
+ <% all_params.each do |param| %>
66
+ <div style="margin-bottom: 0.5rem; padding-bottom: 0.5rem; border-bottom: 1px solid var(--border-color);">
67
+ <div style="display: flex; align-items: center; gap: 0.5rem; margin-bottom: 0.25rem;">
68
+ <code style="font-weight: 600; color: var(--primary-color);"><%= param[:name] %></code>
69
+ <span class="badge" style="font-size: 0.75rem; padding: 0.125rem 0.375rem;"><%= param[:type] %></span>
70
+ <% if param[:required] %>
71
+ <span style="color: #dc2626; font-size: 0.75rem; font-weight: 600;">required</span>
72
+ <% else %>
73
+ <span style="color: #6b7280; font-size: 0.75rem;">optional</span>
74
+ <% end %>
75
+ </div>
76
+ <div style="color: #6b7280; font-size: 0.75rem;">
77
+ Location: <%= param[:location] %>
78
+ </div>
79
+ </div>
80
+ <% end %>
81
+ </div>
82
+ </details>
62
83
  <% else %>
63
- <span style="color: var(--text-muted);">—</span>
84
+ <span style="color: var(--text-muted);">No parameters</span>
64
85
  <% end %>
65
86
  </td>
66
87
  </tr>
@@ -283,7 +283,7 @@
283
283
  </main>
284
284
 
285
285
  <footer style="text-align: center; padding: 2rem; color: var(--text-muted); font-size: 0.875rem;">
286
- Generated by RailsDocGenerator on <%= Time.now.strftime('%Y-%m-%d %H:%M:%S') %>
286
+ Generated by <a href="https://github.com/ArshdeepGrover/rails-map" target="_blank">RailsMap</a> on <%= Time.now.strftime('%Y-%m-%d %H:%M:%S') %>
287
287
  </footer>
288
288
  </body>
289
289
  </html>