spontaneous 0.2.0.alpha7 → 0.2.0.beta1
Sign up to get free protection for your applications and to get access to all the features.
- data/Gemfile +10 -4
- data/Readme.markdown +1 -1
- data/application/css/definitions.css.scss +5 -0
- data/application/css/dialogue.css.scss +62 -0
- data/application/js/content.js +1 -1
- data/application/js/dom.js +1 -1
- data/application/js/event_source.js +3 -0
- data/application/js/{field_types/date_field.js → field/date.js} +2 -2
- data/application/js/{field_types/file_field.js → field/file.js} +2 -2
- data/application/js/{field_types/image_field.js → field/image.js} +54 -20
- data/application/js/{field_types/long_string_field.js → field/long_string.js} +2 -2
- data/application/js/{field_types/markdown_field.js → field/markdown.js} +2 -2
- data/application/js/{field_types/select_field.js → field/select.js} +2 -2
- data/application/js/{field_types/string_field.js → field/string.js} +21 -7
- data/application/js/{field_types/webvideo_field.js → field/webvideo.js} +2 -2
- data/application/js/field.js +2 -2
- data/application/js/publish.js +99 -19
- data/application/js/spontaneous.js +8 -8
- data/application/js/top_bar.js +6 -4
- data/db/migrations/20130109125023_add_page_publish_lock.rb +17 -0
- data/db/migrations/20130111161934_convert_bcrypt_passwords.rb +22 -0
- data/db/migrations/20130114120000_create_revision_tables.rb +106 -0
- data/db/migrations/20130116220423_add_index_to_archive.rb +9 -0
- data/lib/spontaneous/box.rb +53 -18
- data/lib/spontaneous/box_style.rb +2 -3
- data/lib/spontaneous/change.rb +39 -13
- data/lib/spontaneous/cli/fields.rb +29 -0
- data/lib/spontaneous/cli/init.rb +2 -2
- data/lib/spontaneous/cli/migrate.rb +0 -1
- data/lib/spontaneous/cli/server.rb +14 -10
- data/lib/spontaneous/cli/site.rb +20 -9
- data/lib/spontaneous/cli.rb +8 -6
- data/lib/spontaneous/collections/box_set.rb +11 -0
- data/lib/spontaneous/collections/field_set.rb +24 -1
- data/lib/spontaneous/concern.rb +37 -0
- data/lib/spontaneous/config.rb +3 -4
- data/lib/spontaneous/crypt/version.rb +130 -0
- data/lib/spontaneous/crypt.rb +84 -0
- data/lib/spontaneous/data_mapper/content_model/associations.rb +199 -0
- data/lib/spontaneous/data_mapper/content_model/column_accessors.rb +52 -0
- data/lib/spontaneous/data_mapper/content_model/instance_hooks.rb +34 -0
- data/lib/spontaneous/data_mapper/content_model/serialization.rb +54 -0
- data/lib/spontaneous/data_mapper/content_model/timestamps.rb +39 -0
- data/lib/spontaneous/data_mapper/content_model.rb +343 -0
- data/lib/spontaneous/data_mapper/content_table.rb +103 -0
- data/lib/spontaneous/data_mapper/dataset.rb +194 -0
- data/lib/spontaneous/data_mapper/scope.rb +195 -0
- data/lib/spontaneous/data_mapper.rb +161 -0
- data/lib/spontaneous/facet.rb +2 -2
- data/lib/spontaneous/field/base.rb +418 -0
- data/lib/spontaneous/field/date.rb +54 -0
- data/lib/spontaneous/{field_version.rb → field/field_version.rb} +1 -1
- data/lib/spontaneous/field/file.rb +100 -0
- data/lib/spontaneous/{field_types/image_field.rb → field/image.rb} +33 -33
- data/lib/spontaneous/{field_types/location_field.rb → field/location.rb} +2 -2
- data/lib/spontaneous/{field_types/long_string_field.rb → field/long_string.rb} +3 -3
- data/lib/spontaneous/field/markdown.rb +36 -0
- data/lib/spontaneous/{field_types/select_field.rb → field/select.rb} +4 -5
- data/lib/spontaneous/field/string.rb +17 -0
- data/lib/spontaneous/field/update.rb +156 -0
- data/lib/spontaneous/field/webvideo.rb +310 -0
- data/lib/spontaneous/field.rb +80 -0
- data/lib/spontaneous/generators/site/Gemfile.tt +2 -2
- data/lib/spontaneous/generators/site/config/environments/development.rb.tt +1 -1
- data/lib/spontaneous/generators/site/config/environments/production.rb.tt +1 -1
- data/lib/spontaneous/generators/site/lib/content.rb.tt +6 -0
- data/lib/spontaneous/generators/site/schema/box.rb.tt +3 -2
- data/lib/spontaneous/generators/site/schema/page.rb.tt +3 -1
- data/lib/spontaneous/generators/site/schema/piece.rb.tt +3 -1
- data/lib/spontaneous/generators/site/templates/layouts/standard.html.cut.tt +3 -1
- data/lib/spontaneous/generators/site.rb +4 -3
- data/lib/spontaneous/image_size.rb +8 -1
- data/lib/spontaneous/layout.rb +5 -1
- data/lib/spontaneous/loader.rb +2 -5
- data/lib/spontaneous/media/file.rb +11 -2
- data/lib/spontaneous/media/temp_file.rb +23 -0
- data/lib/spontaneous/media.rb +20 -39
- data/lib/spontaneous/{plugins → model/box}/allowed_types.rb +38 -17
- data/lib/spontaneous/model/box.rb +18 -0
- data/lib/spontaneous/{plugins → model/core}/aliases.rb +10 -14
- data/lib/spontaneous/{plugins → model/core}/boxes.rb +2 -2
- data/lib/spontaneous/{plugins → model/core}/content_groups.rb +2 -2
- data/lib/spontaneous/model/core/editor_class.rb +4 -0
- data/lib/spontaneous/{plugins → model/core}/entries.rb +19 -7
- data/lib/spontaneous/{plugins → model/core}/entry.rb +3 -3
- data/lib/spontaneous/{plugins → model/core}/fields.rb +38 -5
- data/lib/spontaneous/{plugins → model/core}/instance_code.rb +2 -2
- data/lib/spontaneous/{plugins → model/core}/media.rb +2 -12
- data/lib/spontaneous/{plugins → model/core}/modifications.rb +7 -6
- data/lib/spontaneous/model/core/page_search.rb +36 -0
- data/lib/spontaneous/{plugins → model/core}/permissions.rb +4 -4
- data/lib/spontaneous/{plugins → model/core}/prototypes.rb +4 -4
- data/lib/spontaneous/{plugins → model/core}/publishing.rb +93 -115
- data/lib/spontaneous/{plugins → model/core}/render.rb +2 -2
- data/lib/spontaneous/{plugins → model/core}/schema_hierarchy.rb +7 -11
- data/lib/spontaneous/model/core/schema_id.rb +65 -0
- data/lib/spontaneous/{plugins → model/core}/schema_title.rb +2 -2
- data/lib/spontaneous/{plugins → model/core}/serialisation.rb +2 -2
- data/lib/spontaneous/{plugins → model/core}/styles.rb +2 -2
- data/lib/spontaneous/{plugins → model/core}/supertype.rb +2 -2
- data/lib/spontaneous/{plugins → model/core}/visibility.rb +7 -48
- data/lib/spontaneous/model/core.rb +143 -0
- data/lib/spontaneous/{plugins → model/page}/controllers.rb +3 -3
- data/lib/spontaneous/{plugins → model}/page/formats.rb +2 -2
- data/lib/spontaneous/{plugins → model/page}/layouts.rb +2 -2
- data/lib/spontaneous/model/page/locks.rb +14 -0
- data/lib/spontaneous/{plugins → model/page}/page_tree.rb +3 -3
- data/lib/spontaneous/{plugins → model/page}/paths.rb +30 -12
- data/lib/spontaneous/{plugins → model}/page/request.rb +2 -2
- data/lib/spontaneous/{plugins → model/page}/site_map.rb +2 -2
- data/lib/spontaneous/model/page/site_timestamps.rb +44 -0
- data/lib/spontaneous/{page.rb → model/page.rb} +49 -28
- data/lib/spontaneous/{piece.rb → model/piece.rb} +7 -6
- data/lib/spontaneous/model.rb +97 -0
- data/lib/spontaneous/output/context.rb +1 -1
- data/lib/spontaneous/output/format.rb +4 -0
- data/lib/spontaneous/output/template/renderer.rb +2 -2
- data/lib/spontaneous/output.rb +2 -2
- data/lib/spontaneous/page_lock.rb +62 -0
- data/lib/spontaneous/page_piece.rb +1 -1
- data/lib/spontaneous/permissions/access_key.rb +9 -4
- data/lib/spontaneous/permissions/user.rb +19 -9
- data/lib/spontaneous/permissions.rb +2 -5
- data/lib/spontaneous/plugins/application/facets.rb +1 -2
- data/lib/spontaneous/plugins/application/features.rb +1 -1
- data/lib/spontaneous/plugins/application/paths.rb +1 -1
- data/lib/spontaneous/plugins/application/render.rb +1 -1
- data/lib/spontaneous/plugins/application/serialisation.rb +1 -1
- data/lib/spontaneous/plugins/application/state.rb +30 -1
- data/lib/spontaneous/plugins/application/system.rb +12 -12
- data/lib/spontaneous/prototypes/box_prototype.rb +1 -1
- data/lib/spontaneous/prototypes/field_prototype.rb +3 -6
- data/lib/spontaneous/prototypes/style_prototype.rb +1 -1
- data/lib/spontaneous/publishing/immediate.rb +77 -49
- data/lib/spontaneous/publishing/revision.rb +355 -0
- data/lib/spontaneous/publishing/simultaneous.rb +10 -49
- data/lib/spontaneous/publishing.rb +1 -0
- data/lib/spontaneous/rack/around_back.rb +1 -1
- data/lib/spontaneous/rack/around_front.rb +2 -4
- data/lib/spontaneous/rack/around_preview.rb +1 -1
- data/lib/spontaneous/rack/back.rb +80 -63
- data/lib/spontaneous/rack/cacheable_file.rb +2 -2
- data/lib/spontaneous/rack/cookie_authentication.rb +1 -1
- data/lib/spontaneous/rack/front.rb +1 -1
- data/lib/spontaneous/rack/helpers.rb +8 -9
- data/lib/spontaneous/{page_controller.rb → rack/page_controller.rb} +1 -1
- data/lib/spontaneous/rack/public.rb +3 -3
- data/lib/spontaneous/rack.rb +15 -15
- data/lib/spontaneous/schema/uid.rb +4 -1
- data/lib/spontaneous/schema.rb +57 -24
- data/lib/spontaneous/search/database.rb +12 -1
- data/lib/spontaneous/search/index.rb +34 -6
- data/lib/spontaneous/search/results.rb +1 -1
- data/lib/spontaneous/server.rb +3 -3
- data/lib/spontaneous/simultaneous.rb +53 -0
- data/lib/spontaneous/{plugins/site → site}/features.rb +2 -2
- data/lib/spontaneous/{plugins/site → site}/helpers.rb +2 -3
- data/lib/spontaneous/{plugins/site → site}/hooks.rb +2 -2
- data/lib/spontaneous/{plugins/site → site}/instance.rb +4 -6
- data/lib/spontaneous/{plugins/site → site}/level.rb +2 -2
- data/lib/spontaneous/{plugins/site → site}/map.rb +4 -4
- data/lib/spontaneous/{plugins/site → site}/paths.rb +2 -2
- data/lib/spontaneous/site/publishing.rb +89 -0
- data/lib/spontaneous/{plugins/site → site}/schema.rb +4 -4
- data/lib/spontaneous/{plugins/site → site}/search.rb +2 -2
- data/lib/spontaneous/{plugins/site → site}/selectors.rb +15 -7
- data/lib/spontaneous/{plugins/site → site}/state.rb +2 -2
- data/lib/spontaneous/{plugins/site → site}/storage.rb +2 -2
- data/lib/spontaneous/{plugins/site → site}/url.rb +2 -2
- data/lib/spontaneous/site.rb +31 -14
- data/lib/spontaneous/state.rb +5 -6
- data/lib/spontaneous/style.rb +3 -2
- data/lib/spontaneous/utils/database/mysql_dumper.rb +13 -0
- data/lib/spontaneous/utils/database/postgres_dumper.rb +5 -0
- data/lib/spontaneous/version.rb +1 -1
- data/lib/spontaneous.rb +34 -89
- data/spontaneous.gemspec +112 -114
- data/test/experimental/test_crypt.rb +158 -0
- data/test/experimental/test_features.rb +3 -3
- data/test/fixtures/example_application/config/environments/development.rb +1 -1
- data/test/fixtures/example_application/lib/content.rb +5 -0
- data/test/fixtures/example_application/schema/page.rb +2 -1
- data/test/fixtures/example_application/schema/piece.rb +3 -2
- data/test/fixtures/serialisation/class_hash.yaml.erb +5 -5
- data/test/fixtures/serialisation/root_hash.yaml.erb +8 -0
- data/test/functional/test_application.rb +12 -1
- data/test/functional/test_back.rb +80 -48
- data/test/functional/test_front.rb +39 -46
- data/test/functional/test_user_manager.rb +3 -9
- data/test/javascript/test_markdown.rb +2 -2
- data/test/test_helper.rb +78 -23
- data/test/unit/test_alias.rb +21 -15
- data/test/unit/test_asset_bundler.rb +3 -3
- data/test/unit/test_assets.rb +2 -2
- data/test/unit/test_async.rb +7 -6
- data/test/unit/test_authentication.rb +43 -37
- data/test/unit/test_boxes.rb +46 -21
- data/test/unit/test_changesets.rb +65 -20
- data/test/unit/test_config.rb +9 -9
- data/test/unit/test_content.rb +50 -51
- data/test/unit/test_content_inheritance.rb +6 -20
- data/test/unit/test_datamapper.rb +1330 -0
- data/test/unit/test_datamapper_content.rb +214 -0
- data/test/unit/test_fields.rb +543 -54
- data/test/unit/test_formats.rb +2 -3
- data/test/unit/test_generators.rb +6 -6
- data/test/unit/test_helpers.rb +1 -1
- data/test/unit/test_image_size.rb +10 -5
- data/test/unit/test_images.rb +17 -18
- data/test/unit/test_layouts.rb +18 -3
- data/test/unit/test_media.rb +74 -49
- data/test/unit/test_modifications.rb +43 -43
- data/test/unit/test_page.rb +7 -10
- data/test/unit/test_permissions.rb +3 -10
- data/test/unit/test_piece.rb +5 -6
- data/test/unit/test_plugins.rb +7 -14
- data/test/unit/test_prototypes.rb +3 -3
- data/test/unit/test_publishing.rb +49 -27
- data/test/unit/test_render.rb +46 -15
- data/test/unit/test_revisions.rb +124 -127
- data/test/unit/test_schema.rb +53 -58
- data/test/unit/test_search.rb +64 -16
- data/test/unit/test_serialisation.rb +4 -11
- data/test/unit/test_site.rb +11 -12
- data/test/unit/test_structure.rb +2 -5
- data/test/unit/test_styles.rb +22 -24
- data/test/unit/test_type_hierarchy.rb +7 -5
- data/test/unit/test_visibility.rb +79 -55
- metadata +128 -102
- data/lib/sequel/plugins/content_table_inheritance.rb +0 -203
- data/lib/sequel/plugins/scoped_table_name.rb +0 -54
- data/lib/spontaneous/content.rb +0 -129
- data/lib/spontaneous/field_types/date_field.rb +0 -56
- data/lib/spontaneous/field_types/field.rb +0 -302
- data/lib/spontaneous/field_types/file_field.rb +0 -68
- data/lib/spontaneous/field_types/markdown_field.rb +0 -38
- data/lib/spontaneous/field_types/string_field.rb +0 -19
- data/lib/spontaneous/field_types/webvideo_field.rb +0 -313
- data/lib/spontaneous/field_types.rb +0 -38
- data/lib/spontaneous/generators/site/lib/site.rb.tt +0 -4
- data/lib/spontaneous/plugins/field/editor_class.rb +0 -13
- data/lib/spontaneous/plugins/page/site_timestamps.rb +0 -28
- data/lib/spontaneous/plugins/page_search.rb +0 -63
- data/lib/spontaneous/plugins/schema_id.rb +0 -68
- data/lib/spontaneous/plugins/site/publishing.rb +0 -75
- data/lib/spontaneous/rack/fiber_pool.rb +0 -26
- data/test/unit/test_table_scoping.rb +0 -80
@@ -10,14 +10,21 @@ module Spontaneous
|
|
10
10
|
include Assets
|
11
11
|
|
12
12
|
def self.messenger
|
13
|
-
@messenger ||=
|
13
|
+
@messenger ||= event_source
|
14
|
+
end
|
15
|
+
|
16
|
+
def self.event_source
|
17
|
+
messenger = ::Spontaneous::Rack::EventSource.new
|
14
18
|
# Find a way to move this into a more de-centralised place
|
15
19
|
# at some point we are going to want to have some configurable, extendable
|
16
20
|
# list of event handlers
|
17
|
-
Simultaneous.on_event("publish_progress") { |event|
|
18
|
-
|
21
|
+
::Simultaneous.on_event("publish_progress") { |event|
|
22
|
+
messenger.deliver_event(event)
|
23
|
+
}
|
24
|
+
::Simultaneous.on_event("page_lock_status") { |event|
|
25
|
+
messenger.deliver_event(event)
|
19
26
|
}
|
20
|
-
|
27
|
+
messenger
|
21
28
|
end
|
22
29
|
|
23
30
|
class EventSource < ServerBase
|
@@ -36,7 +43,6 @@ module Spontaneous
|
|
36
43
|
|
37
44
|
def self.editing_app
|
38
45
|
::Rack::Builder.app do
|
39
|
-
use Spontaneous::Rack::FiberPool, :size => 15
|
40
46
|
use ::Rack::Lint
|
41
47
|
use Spontaneous::Rack::Static, :root => Spontaneous.application_dir, :urls => %W(/static)
|
42
48
|
use Spontaneous::Rack::Static, :root => Spontaneous.root / "public/@spontaneous", :urls => %W(/assets)
|
@@ -216,53 +222,63 @@ module Spontaneous
|
|
216
222
|
end
|
217
223
|
|
218
224
|
class EditingInterface < AuthenticatedHandler
|
219
|
-
use Reloader if Site.config.reload_classes
|
225
|
+
use Reloader if Spontaneous::Site.config.reload_classes
|
220
226
|
|
221
227
|
set :views, Proc.new { Spontaneous.application_dir + '/views' }
|
222
228
|
|
223
229
|
|
224
230
|
def update_fields(model, field_data)
|
225
|
-
|
226
|
-
|
227
|
-
|
228
|
-
|
229
|
-
|
230
|
-
|
231
|
-
|
232
|
-
|
233
|
-
|
234
|
-
|
235
|
-
|
236
|
-
|
237
|
-
|
238
|
-
|
239
|
-
|
240
|
-
|
241
|
-
|
242
|
-
|
243
|
-
|
244
|
-
|
245
|
-
|
246
|
-
|
247
|
-
|
248
|
-
|
249
|
-
|
250
|
-
|
231
|
+
return unless field_data
|
232
|
+
Spontaneous::Field.update_asynchronously(model, field_data, user)
|
233
|
+
json(model)
|
234
|
+
end
|
235
|
+
|
236
|
+
# def update_fields(model, field_data)
|
237
|
+
# conflicts = []
|
238
|
+
# if field_data
|
239
|
+
# field_data.each do |id, values|
|
240
|
+
# field = model.fields.sid(id)
|
241
|
+
# if model.field_writable?(user, field.name.to_sym)
|
242
|
+
# # version = values.delete("version").to_i
|
243
|
+
# # if version == field.version
|
244
|
+
# field.update(values)
|
245
|
+
# # else
|
246
|
+
# # conflicts << [field, values]
|
247
|
+
# # end
|
248
|
+
# else
|
249
|
+
# unauthorised!
|
250
|
+
# end
|
251
|
+
# end
|
252
|
+
# end
|
253
|
+
# if conflicts.empty?
|
254
|
+
# if model.save
|
255
|
+
# json(model)
|
256
|
+
# end
|
257
|
+
# else
|
258
|
+
# errors = conflicts.map do |field, new_value|
|
259
|
+
# [field.schema_id.to_s, [field.version, field.conflicted_value, new_value["unprocessed_value"]]]
|
260
|
+
# end
|
261
|
+
# [409, json(Hash[errors])]
|
262
|
+
# end
|
263
|
+
# end
|
264
|
+
|
265
|
+
def content_model
|
266
|
+
Spontaneous::Content
|
251
267
|
end
|
252
268
|
|
253
269
|
def content_for_request(lock = false)
|
254
|
-
|
255
|
-
dataset = lock ?
|
256
|
-
content = dataset.
|
270
|
+
content_model.db.transaction do
|
271
|
+
dataset = lock ? content_model.for_update : content_model
|
272
|
+
content = dataset.get(params[:id])
|
257
273
|
halt 404 if content.nil?
|
258
274
|
content.current_editor = user
|
259
|
-
if box_id =
|
275
|
+
if box_id = content_model.schema.uids[params[:box_id]]
|
260
276
|
box = content.boxes.detect { |b| b.schema_id == box_id }
|
261
277
|
yield(content, box)
|
262
278
|
else
|
263
279
|
yield(content)
|
264
280
|
end
|
265
|
-
|
281
|
+
end
|
266
282
|
end
|
267
283
|
|
268
284
|
def set_authentication_cookie(key)
|
@@ -325,7 +341,7 @@ module Spontaneous
|
|
325
341
|
end
|
326
342
|
|
327
343
|
get '/root' do
|
328
|
-
json Site.root
|
344
|
+
json Spontaneous::Site.root
|
329
345
|
end
|
330
346
|
|
331
347
|
get '/page/:id' do
|
@@ -334,15 +350,15 @@ module Spontaneous
|
|
334
350
|
|
335
351
|
get '/metadata' do
|
336
352
|
json({
|
337
|
-
:types => Site.schema.export(user),
|
353
|
+
:types => Spontaneous::Site.schema.export(user),
|
338
354
|
:user => user.export,
|
339
|
-
:services => (Site.config.services || [])
|
355
|
+
:services => (Spontaneous::Site.config.services || [])
|
340
356
|
})
|
341
357
|
end
|
342
358
|
|
343
359
|
get '/map/?:id?' do
|
344
|
-
last_modified(Site.modified_at)
|
345
|
-
map = Site.map(params[:id])
|
360
|
+
last_modified(Spontaneous::Site.modified_at)
|
361
|
+
map = Spontaneous::Site.map(params[:id])
|
346
362
|
if map
|
347
363
|
json(map)
|
348
364
|
else
|
@@ -351,19 +367,19 @@ module Spontaneous
|
|
351
367
|
end
|
352
368
|
|
353
369
|
get '/location*' do
|
354
|
-
last_modified(Site.modified_at)
|
355
|
-
if Page.count == 0
|
370
|
+
last_modified(Spontaneous::Site.modified_at)
|
371
|
+
if content_model::Page.count == 0
|
356
372
|
406
|
357
373
|
else
|
358
374
|
path = params[:splat].first
|
359
|
-
page = Site[path]
|
360
|
-
json Site.map(page.id)
|
375
|
+
page = Spontaneous::Site[path]
|
376
|
+
json Spontaneous::Site.map(page.id)
|
361
377
|
end
|
362
378
|
end
|
363
379
|
|
364
380
|
post '/root' do
|
365
|
-
if Site.root.nil?
|
366
|
-
type =
|
381
|
+
if Spontaneous::Site.root.nil?
|
382
|
+
type = content_model.schema.to_class(params[:type])
|
367
383
|
root = type.create(:title => "Home")
|
368
384
|
json({:id => root.id})
|
369
385
|
else
|
@@ -389,7 +405,7 @@ module Spontaneous
|
|
389
405
|
conflicts = []
|
390
406
|
field_versions.each do |schema_id, version|
|
391
407
|
field = content.fields.sid(schema_id)
|
392
|
-
|
408
|
+
if field.matches_version?(version.to_i)
|
393
409
|
conflicts << field
|
394
410
|
end
|
395
411
|
end
|
@@ -450,8 +466,7 @@ module Spontaneous
|
|
450
466
|
if target.field_writable?(user, field.name)
|
451
467
|
# version = params[:version].to_i
|
452
468
|
# if version == field.version
|
453
|
-
field
|
454
|
-
content.save
|
469
|
+
Spontaneous::Field.set_asynchronously(field, file, user)
|
455
470
|
json(field.export(user))
|
456
471
|
# else
|
457
472
|
# errors = [[field.schema_id.to_s, [field.version, field.conflicted_value]]]
|
@@ -474,8 +489,7 @@ module Spontaneous
|
|
474
489
|
instance = type.new
|
475
490
|
box.insert(position, instance)
|
476
491
|
field = instance.field_for_mime_type(file[:type])
|
477
|
-
field
|
478
|
-
instance.save
|
492
|
+
Spontaneous::Field.set_asynchronously(field, file, user)
|
479
493
|
content.save
|
480
494
|
json({
|
481
495
|
:position => position,
|
@@ -491,7 +505,7 @@ module Spontaneous
|
|
491
505
|
post '/add/:id/:box_id/:type_name' do
|
492
506
|
content_for_request(true) do |content, box|
|
493
507
|
position = (params[:position] || 0).to_i
|
494
|
-
type =
|
508
|
+
type = content_model.schema.to_class(params[:type_name])#.constantize
|
495
509
|
|
496
510
|
if box.writable?(user, type)
|
497
511
|
instance = type.new(:created_by => user)
|
@@ -561,7 +575,7 @@ module Spontaneous
|
|
561
575
|
end
|
562
576
|
|
563
577
|
get '/targets/:schema_id/:id/:box_id' do
|
564
|
-
klass =
|
578
|
+
klass = content_model.schema.to_class(params[:schema_id])
|
565
579
|
if klass.alias?
|
566
580
|
content_for_request do |content, box|
|
567
581
|
options = {}
|
@@ -585,7 +599,7 @@ module Spontaneous
|
|
585
599
|
|
586
600
|
post '/alias/:id/:box_id' do
|
587
601
|
content_for_request(true) do |content, box|
|
588
|
-
type =
|
602
|
+
type = content_model.schema.to_class(params[:alias_id])
|
589
603
|
position = (params[:position] || 0).to_i
|
590
604
|
if box.writable?(user, type)
|
591
605
|
instance = type.for_target(params[:target_id])
|
@@ -619,7 +633,7 @@ module Spontaneous
|
|
619
633
|
400
|
620
634
|
else
|
621
635
|
if user.level.can_publish?
|
622
|
-
Site.publish_pages(pages)
|
636
|
+
Spontaneous::Site.publish_pages(pages)
|
623
637
|
json({})
|
624
638
|
else
|
625
639
|
unauthorised!
|
@@ -664,11 +678,10 @@ module Spontaneous
|
|
664
678
|
# version = params[:version].to_i
|
665
679
|
# if version == field.version
|
666
680
|
Spontaneous::Media.combine_shards(params[:shards]) do |combined|
|
667
|
-
field
|
681
|
+
Spontaneous::Field.set_asynchronously(field, {
|
668
682
|
:filename => params[:filename],
|
669
683
|
:tempfile => combined
|
670
|
-
}
|
671
|
-
target.save
|
684
|
+
}, user)
|
672
685
|
end
|
673
686
|
json(field.export(user))
|
674
687
|
# else
|
@@ -691,11 +704,15 @@ module Spontaneous
|
|
691
704
|
box.insert(position, instance)
|
692
705
|
field = instance.field_for_mime_type(params[:mime_type])
|
693
706
|
Spontaneous::Media.combine_shards(params[:shards]) do |combined|
|
694
|
-
field
|
707
|
+
Spontaneous::Field.set_asynchronously(field, {
|
695
708
|
:filename => params[:filename],
|
696
709
|
:tempfile => combined
|
697
|
-
}
|
710
|
+
}, user)
|
698
711
|
content.save
|
712
|
+
# field.value = {
|
713
|
+
# :filename => params[:filename],
|
714
|
+
# :tempfile => combined
|
715
|
+
# }
|
699
716
|
end
|
700
717
|
json({
|
701
718
|
:position => position,
|
@@ -757,7 +774,7 @@ module Spontaneous
|
|
757
774
|
class Preview < Sinatra::Base
|
758
775
|
use CookieAuthentication
|
759
776
|
use AroundPreview
|
760
|
-
use Reloader if Site.config.reload_classes
|
777
|
+
use Reloader if Spontaneous::Site.config.reload_classes
|
761
778
|
include Spontaneous::Rack::Public
|
762
779
|
helpers Spontaneous::Rack::UserHelpers
|
763
780
|
|
@@ -3,7 +3,7 @@ module Spontaneous::Rack
|
|
3
3
|
class CacheableFile < ::Rack::File
|
4
4
|
include HTTP
|
5
5
|
|
6
|
-
TEN_YEARS = 10*365*24*3600
|
6
|
+
TEN_YEARS = 10*365.25*24*3600
|
7
7
|
MAX_AGE = "max-age=#{TEN_YEARS}, public".freeze
|
8
8
|
|
9
9
|
def initialize(file_root)
|
@@ -20,7 +20,7 @@ module Spontaneous::Rack
|
|
20
20
|
def caching_headers(headers)
|
21
21
|
headers.merge({
|
22
22
|
HTTP_CACHE_CONTROL => MAX_AGE,
|
23
|
-
HTTP_EXPIRES => (Time.now
|
23
|
+
HTTP_EXPIRES => (Time.now.advance(:years => 10)).httpdate
|
24
24
|
})
|
25
25
|
end
|
26
26
|
end
|
@@ -9,7 +9,7 @@ module Spontaneous
|
|
9
9
|
|
10
10
|
def access_key(env)
|
11
11
|
if login = Site.config.auto_login
|
12
|
-
user = Spontaneous::Permissions::User
|
12
|
+
user = Spontaneous::Permissions::User.login(login)
|
13
13
|
if user.access_keys.empty?
|
14
14
|
user.generate_access_key(env["REMOTE_ADDR"])
|
15
15
|
else
|
@@ -15,22 +15,21 @@ module Spontaneous
|
|
15
15
|
end
|
16
16
|
|
17
17
|
def style_url(style)
|
18
|
-
style
|
19
|
-
if (compiled_asset = application_assets.manifest.assets[style])
|
20
|
-
return "#{NAMESPACE}/assets/#{compiled_asset}"
|
21
|
-
end
|
22
|
-
# TODO: use the sprockets environment to append a modification time to the non-compiled URL
|
23
|
-
"#{NAMESPACE}/css/#{style}"
|
18
|
+
asset_url(style, "css")
|
24
19
|
end
|
25
20
|
|
26
21
|
def script_url(script)
|
27
|
-
script
|
22
|
+
asset_url(script, "js")
|
23
|
+
end
|
24
|
+
|
25
|
+
def asset_url(file, type)
|
26
|
+
file = "#{file}.#{type}" unless file =~ /\.#{type}$/
|
28
27
|
|
29
|
-
if (compiled_asset = application_assets.manifest.assets[
|
28
|
+
if (compiled_asset = application_assets.manifest.assets[file])
|
30
29
|
return "#{NAMESPACE}/assets/#{compiled_asset}"
|
31
30
|
end
|
32
31
|
# TODO: use the sprockets environment to append a modification time to the non-compiled URL
|
33
|
-
"#{NAMESPACE}
|
32
|
+
"#{NAMESPACE}/#{type}/#{file}"
|
34
33
|
end
|
35
34
|
|
36
35
|
def script_list(scripts)
|
@@ -81,7 +81,7 @@ module Spontaneous
|
|
81
81
|
end
|
82
82
|
|
83
83
|
DOT = '.'.freeze
|
84
|
-
ACTION = "/#{S::
|
84
|
+
ACTION = "/#{S::Model::Page::Controllers::ACTION_SEPARATOR}".freeze
|
85
85
|
|
86
86
|
def show(page, status=200)
|
87
87
|
page = Spontaneous::Site[page] if String === page
|
@@ -101,7 +101,7 @@ module Spontaneous
|
|
101
101
|
|
102
102
|
def redirect(location, redirect_code=:temporary)
|
103
103
|
if String === location
|
104
|
-
destination = Site[location]
|
104
|
+
destination = Spontaneous::Site[location]
|
105
105
|
location = destination.path if destination and destination.respond_to?(:path)
|
106
106
|
else
|
107
107
|
location = location.path if location.respond_to?(:path)
|
@@ -129,7 +129,7 @@ module Spontaneous
|
|
129
129
|
|
130
130
|
def find_page!(path)
|
131
131
|
@path, @output, @action = parse_path(path)
|
132
|
-
@page = Site[@path]
|
132
|
+
@page = Spontaneous::Site[@path]
|
133
133
|
end
|
134
134
|
|
135
135
|
def output
|
data/lib/spontaneous/rack.rb
CHANGED
@@ -45,27 +45,27 @@ module Spontaneous
|
|
45
45
|
set :environment, Proc.new { Spontaneous.environment }
|
46
46
|
end
|
47
47
|
|
48
|
-
autoload :
|
48
|
+
autoload :AroundBack, 'spontaneous/rack/around_back'
|
49
|
+
autoload :AroundFront, 'spontaneous/rack/around_front'
|
50
|
+
autoload :AroundPreview, 'spontaneous/rack/around_preview'
|
49
51
|
autoload :Assets, 'spontaneous/rack/assets'
|
50
|
-
autoload :Back, 'spontaneous/rack/back'
|
51
|
-
autoload :Front, 'spontaneous/rack/front'
|
52
|
-
autoload :Public, 'spontaneous/rack/public'
|
53
52
|
autoload :Authentication, 'spontaneous/rack/authentication'
|
53
|
+
autoload :Back, 'spontaneous/rack/back'
|
54
|
+
autoload :CSS, 'spontaneous/rack/css'
|
54
55
|
autoload :CacheableFile, 'spontaneous/rack/cacheable_file'
|
55
|
-
autoload :Static, 'spontaneous/rack/static'
|
56
|
-
autoload :UserHelpers, 'spontaneous/rack/user_helpers'
|
57
|
-
autoload :UserAdmin, 'spontaneous/rack/user_admin'
|
58
|
-
autoload :Helpers, 'spontaneous/rack/helpers'
|
59
56
|
autoload :CookieAuthentication, 'spontaneous/rack/cookie_authentication'
|
60
|
-
autoload :QueryAuthentication, 'spontaneous/rack/query_authentication'
|
61
|
-
autoload :AroundBack, 'spontaneous/rack/around_back'
|
62
|
-
autoload :AroundFront, 'spontaneous/rack/around_front'
|
63
|
-
autoload :AroundPreview, 'spontaneous/rack/around_preview'
|
64
|
-
autoload :Reloader, 'spontaneous/rack/reloader'
|
65
57
|
autoload :EventSource, 'spontaneous/rack/event_source'
|
66
|
-
autoload :
|
58
|
+
autoload :Front, 'spontaneous/rack/front'
|
59
|
+
autoload :HTTP, 'spontaneous/rack/http'
|
60
|
+
autoload :Helpers, 'spontaneous/rack/helpers'
|
67
61
|
autoload :JS, 'spontaneous/rack/js'
|
62
|
+
autoload :PageController, "spontaneous/rack/page_controller"
|
63
|
+
autoload :Public, 'spontaneous/rack/public'
|
64
|
+
autoload :QueryAuthentication, 'spontaneous/rack/query_authentication'
|
65
|
+
autoload :Reloader, 'spontaneous/rack/reloader'
|
68
66
|
autoload :SSE, 'spontaneous/rack/sse'
|
69
|
-
autoload :
|
67
|
+
autoload :Static, 'spontaneous/rack/static'
|
68
|
+
autoload :UserAdmin, 'spontaneous/rack/user_admin'
|
69
|
+
autoload :UserHelpers, 'spontaneous/rack/user_helpers'
|
70
70
|
end
|
71
71
|
end
|
@@ -124,6 +124,10 @@ module Spontaneous
|
|
124
124
|
@id
|
125
125
|
end
|
126
126
|
|
127
|
+
def sql_literal(dataset)
|
128
|
+
dataset.literal @id
|
129
|
+
end
|
130
|
+
|
127
131
|
def <=>(other)
|
128
132
|
self.to_s <=> other.to_s
|
129
133
|
end
|
@@ -132,6 +136,5 @@ module Spontaneous
|
|
132
136
|
%(#<#{self.class}:"#{@id}" => "#{reference}">)
|
133
137
|
end
|
134
138
|
end
|
135
|
-
|
136
139
|
end
|
137
140
|
end
|
data/lib/spontaneous/schema.rb
CHANGED
@@ -16,7 +16,7 @@ module Spontaneous
|
|
16
16
|
load_map
|
17
17
|
end
|
18
18
|
|
19
|
-
def
|
19
|
+
def to_id(obj)
|
20
20
|
reference_to_id(obj.schema_name)
|
21
21
|
end
|
22
22
|
|
@@ -24,7 +24,7 @@ module Spontaneous
|
|
24
24
|
uids.get_id(reference)
|
25
25
|
end
|
26
26
|
|
27
|
-
def
|
27
|
+
def to_class(id)
|
28
28
|
if uid = uids[id]
|
29
29
|
uid.target
|
30
30
|
else
|
@@ -78,7 +78,7 @@ module Spontaneous
|
|
78
78
|
@uids = uids
|
79
79
|
end
|
80
80
|
|
81
|
-
def
|
81
|
+
def to_id(obj)
|
82
82
|
if id = super
|
83
83
|
id
|
84
84
|
else
|
@@ -99,12 +99,18 @@ module Spontaneous
|
|
99
99
|
end
|
100
100
|
end
|
101
101
|
|
102
|
+
def self.new(root, schema_loader_class = Spontaneous::Schema::PersistentMap)
|
103
|
+
Schema.new(root, schema_loader_class)
|
104
|
+
end
|
105
|
+
|
102
106
|
class Schema
|
103
|
-
|
107
|
+
attr_accessor :schema_loader_class
|
108
|
+
attr_reader :uids
|
104
109
|
|
105
110
|
def initialize(root, schema_loader_class = Spontaneous::Schema::PersistentMap)
|
106
111
|
@root = root
|
107
112
|
@schema_loader_class = schema_loader_class
|
113
|
+
@subclass_map = Hash.new { |h, k| h[k] = [] }
|
108
114
|
initialize_uid_map
|
109
115
|
end
|
110
116
|
|
@@ -250,38 +256,53 @@ module Spontaneous
|
|
250
256
|
Spontaneous.serialise_http(export(user))
|
251
257
|
end
|
252
258
|
|
259
|
+
def unfiltered_classes
|
260
|
+
@classes ||= []
|
261
|
+
end
|
262
|
+
|
253
263
|
# all classes including boxes
|
254
264
|
def classes
|
255
|
-
|
265
|
+
unfiltered_classes.reject { |c| is_excluded_type?(c) }
|
256
266
|
end
|
257
267
|
|
258
|
-
def
|
268
|
+
def inherited(supertype, type)
|
259
269
|
inheritance_map[supertype.to_s] << type
|
260
|
-
|
270
|
+
unfiltered_classes << type
|
271
|
+
end
|
272
|
+
|
273
|
+
def is_excluded_type?(type)
|
274
|
+
excluded_types.include?(type)
|
275
|
+
end
|
276
|
+
|
277
|
+
def excluded_types
|
278
|
+
[Spontaneous::Content, Spontaneous::Content::Page, Spontaneous::Content::Piece]
|
261
279
|
end
|
262
280
|
|
263
281
|
def inheritance_map
|
264
|
-
@inheritance_map ||=
|
282
|
+
@inheritance_map ||= empty_inheritance_map
|
265
283
|
end
|
266
284
|
|
285
|
+
def empty_inheritance_map
|
286
|
+
Hash.new { |h, k| h[k] = [] }
|
287
|
+
end
|
267
288
|
|
268
289
|
def subclasses_of(type)
|
269
290
|
inheritance_map[type.to_s].map { |subclass| subclass }
|
270
291
|
end
|
271
292
|
|
272
293
|
def descendents_of(type)
|
273
|
-
subclasses_of(type).
|
294
|
+
subclasses_of(type).flat_map{ |x| [x] + descendents_of(x) }
|
274
295
|
end
|
275
296
|
|
297
|
+
alias_method :subclasses, :descendents_of
|
298
|
+
|
276
299
|
# just subclasses of Content (excluding boxes)
|
277
300
|
# only need this for the serialisation (which doesn't include boxes)
|
301
|
+
#
|
302
|
+
# TODO: Find a way to filter out the top-level classes without hard-coding
|
303
|
+
# them here.
|
278
304
|
def content_classes
|
279
|
-
classes
|
280
|
-
self.classes.reject { |k| k.is_box? }.each do |klass|
|
281
|
-
classes << klass unless [Spontaneous::Page, Spontaneous::Piece].include?(klass)
|
282
|
-
# recurse_classes(klass, classes)
|
283
|
-
end
|
284
|
-
classes.uniq
|
305
|
+
classes.reject { |k| k.is_box? }.uniq
|
285
306
|
end
|
286
307
|
|
287
308
|
def recurse_classes(root_class, list)
|
@@ -291,16 +312,14 @@ module Spontaneous
|
|
291
312
|
end
|
292
313
|
end
|
293
314
|
|
294
|
-
# should only be used in tests
|
295
315
|
def reset!
|
296
|
-
|
297
|
-
@classes = []
|
316
|
+
@classes = []
|
298
317
|
@inheritance_map = nil
|
299
318
|
reload!
|
300
319
|
end
|
301
320
|
|
302
321
|
def reload!
|
303
|
-
@map
|
322
|
+
@map = nil
|
304
323
|
initialize_uid_map
|
305
324
|
end
|
306
325
|
|
@@ -308,8 +327,22 @@ module Spontaneous
|
|
308
327
|
@uids = Spontaneous::Schema::UIDMap.new
|
309
328
|
end
|
310
329
|
|
330
|
+
# It's obvious from this method that schema classes are
|
331
|
+
# stored in too many ways
|
311
332
|
def delete(klass)
|
312
|
-
|
333
|
+
constants_of(klass).each { |const| delete(const) }
|
334
|
+
unfiltered_classes.delete(klass)
|
335
|
+
remove_group_members(klass)
|
336
|
+
inheritance_map.delete(klass.to_s)
|
337
|
+
inheritance_map.each do |supertype, subtypes|
|
338
|
+
subtypes.delete(klass)
|
339
|
+
end
|
340
|
+
end
|
341
|
+
|
342
|
+
def constants_of(klass)
|
343
|
+
klass.constants.
|
344
|
+
select { |c| klass.const_defined?(c, false) }.
|
345
|
+
map { |c| klass.const_get(c) }
|
313
346
|
end
|
314
347
|
|
315
348
|
def schema_map_file
|
@@ -326,12 +359,12 @@ module Spontaneous
|
|
326
359
|
@map ||= self.schema_loader_class.new(@uids, schema_map_file)
|
327
360
|
end
|
328
361
|
|
329
|
-
def
|
330
|
-
map.
|
362
|
+
def to_id(obj)
|
363
|
+
map.to_id(obj)
|
331
364
|
end
|
332
365
|
|
333
|
-
def
|
334
|
-
map
|
366
|
+
def to_class(id)
|
367
|
+
map.to_class(id)
|
335
368
|
end
|
336
369
|
|
337
370
|
def groups
|
@@ -26,12 +26,22 @@ module Spontaneous::Search
|
|
26
26
|
options = { :dir => directory,
|
27
27
|
:language => @index.language,
|
28
28
|
:fields => @index.fields,
|
29
|
-
:spelling => true
|
29
|
+
:spelling => true,
|
30
|
+
:weights => weighting_proc
|
31
|
+
}
|
30
32
|
options[:stemmer] = @index.stemmer unless @index.stemmer.nil?
|
31
33
|
options[:stopper] = @index.stopper unless @index.stopper.nil?
|
32
34
|
options
|
33
35
|
end
|
34
36
|
|
37
|
+
def weighting_proc
|
38
|
+
Proc.new { |key, value, fields| field_weighting(key, fields) }
|
39
|
+
end
|
40
|
+
|
41
|
+
def field_weighting(key, fields)
|
42
|
+
@weights[key]
|
43
|
+
end
|
44
|
+
|
35
45
|
def database
|
36
46
|
@database ||= open_database
|
37
47
|
end
|
@@ -42,6 +52,7 @@ module Spontaneous::Search
|
|
42
52
|
|
43
53
|
def add(page)
|
44
54
|
if @index.include?(page)
|
55
|
+
@weights = @index.weights(page)
|
45
56
|
database << @index.indexable_content(page)
|
46
57
|
end
|
47
58
|
end
|