talia_core 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.
- data/README.rdoc +41 -0
- data/bin/talia +33 -0
- data/lib/JXslt/jxslt.rb +60 -0
- data/lib/acts_as_roled.rb +11 -0
- data/lib/core_ext/platform.rb +9 -0
- data/lib/core_ext/string.rb +6 -0
- data/lib/core_ext.rb +1 -0
- data/lib/custom_template.rb +4 -0
- data/lib/loader_helper.rb +62 -0
- data/lib/mysql.rb +1214 -0
- data/lib/progressbar.rb +236 -0
- data/lib/role.rb +12 -0
- data/lib/talia_cl/command_line.rb +39 -0
- data/lib/talia_cl/commands/standalone/cl_options.rb +9 -0
- data/lib/talia_cl/commands/standalone/standalone_generate.rb +75 -0
- data/lib/talia_cl/commands/standalone.rb +25 -0
- data/lib/talia_cl/commands/talia_console/cl_options.rb +55 -0
- data/lib/talia_cl/commands/talia_console/console_commands.rb +37 -0
- data/lib/talia_cl/commands/talia_console/talia_commands.rb +131 -0
- data/lib/talia_cl/commands/talia_console.rb +47 -0
- data/lib/talia_cl/core_commands.rb +11 -0
- data/lib/talia_cl.rb +47 -0
- data/lib/talia_core/active_source.rb +372 -0
- data/lib/talia_core/active_source_parts/class_methods.rb +378 -0
- data/lib/talia_core/active_source_parts/predicate_handler.rb +89 -0
- data/lib/talia_core/active_source_parts/rdf.rb +131 -0
- data/lib/talia_core/active_source_parts/sql_helper.rb +36 -0
- data/lib/talia_core/active_source_parts/xml/base_builder.rb +47 -0
- data/lib/talia_core/active_source_parts/xml/generic_reader.rb +363 -0
- data/lib/talia_core/active_source_parts/xml/rdf_builder.rb +88 -0
- data/lib/talia_core/active_source_parts/xml/source_builder.rb +73 -0
- data/lib/talia_core/active_source_parts/xml/source_reader.rb +20 -0
- data/lib/talia_core/agent.rb +14 -0
- data/lib/talia_core/background_jobs/job.rb +82 -0
- data/lib/talia_core/background_jobs/progress_job.rb +68 -0
- data/lib/talia_core/collection.rb +13 -0
- data/lib/talia_core/data_types/data_loader.rb +92 -0
- data/lib/talia_core/data_types/data_record.rb +105 -0
- data/lib/talia_core/data_types/delayed_copier.rb +76 -0
- data/lib/talia_core/data_types/file_record.rb +59 -0
- data/lib/talia_core/data_types/file_store.rb +306 -0
- data/lib/talia_core/data_types/iip_data.rb +153 -0
- data/lib/talia_core/data_types/iip_loader.rb +127 -0
- data/lib/talia_core/data_types/image_data.rb +32 -0
- data/lib/talia_core/data_types/media_link.rb +19 -0
- data/lib/talia_core/data_types/mime_mapping.rb +45 -0
- data/lib/talia_core/data_types/path_helpers.rb +77 -0
- data/lib/talia_core/data_types/pdf_data.rb +42 -0
- data/lib/talia_core/data_types/simple_text.rb +36 -0
- data/lib/talia_core/data_types/temp_file_handling.rb +85 -0
- data/lib/talia_core/data_types/xml_data.rb +169 -0
- data/lib/talia_core/dc_resource.rb +20 -0
- data/lib/talia_core/dummy_handler.rb +34 -0
- data/lib/talia_core/dummy_source.rb +20 -0
- data/lib/talia_core/errors.rb +25 -0
- data/lib/talia_core/initializer.rb +427 -0
- data/lib/talia_core/ordered_source.rb +228 -0
- data/lib/talia_core/rails_ext/actionpack/action_controller/record_identifier.rb +13 -0
- data/lib/talia_core/rails_ext/actionpack/action_controller.rb +1 -0
- data/lib/talia_core/rails_ext/actionpack.rb +1 -0
- data/lib/talia_core/rails_ext.rb +1 -0
- data/lib/talia_core/rdf_import.rb +90 -0
- data/lib/talia_core/rdf_resource.rb +159 -0
- data/lib/talia_core/semantic_collection_item.rb +93 -0
- data/lib/talia_core/semantic_collection_wrapper.rb +324 -0
- data/lib/talia_core/semantic_property.rb +7 -0
- data/lib/talia_core/semantic_relation.rb +67 -0
- data/lib/talia_core/source.rb +323 -0
- data/lib/talia_core/source_transfer_object.rb +38 -0
- data/lib/talia_core/workflow/base.rb +15 -0
- data/lib/talia_core/workflow/publication_workflow.rb +62 -0
- data/lib/talia_core/workflow.rb +300 -0
- data/lib/talia_core.rb +9 -0
- data/lib/talia_dependencies.rb +12 -0
- data/lib/talia_util/bar_progressor.rb +15 -0
- data/lib/talia_util/configuration/config_file.rb +48 -0
- data/lib/talia_util/configuration/database_config.rb +40 -0
- data/lib/talia_util/configuration/mysql_database_setup.rb +104 -0
- data/lib/talia_util/data_import.rb +91 -0
- data/lib/talia_util/image_conversions.rb +82 -0
- data/lib/talia_util/import_job_helper.rb +132 -0
- data/lib/talia_util/io_helper.rb +54 -0
- data/lib/talia_util/progressable.rb +38 -0
- data/lib/talia_util/progressbar.rb +236 -0
- data/lib/talia_util/rdf_update.rb +80 -0
- data/lib/talia_util/some_sigla.xml +1960 -0
- data/lib/talia_util/test_helpers.rb +151 -0
- data/lib/talia_util/util.rb +226 -0
- data/lib/talia_util/yaml_import.rb +80 -0
- data/lib/talia_util.rb +13 -0
- data/lib/user.rb +116 -0
- data/lib/version.rb +15 -0
- data/test/core_ext/string_test.rb +11 -0
- data/test/custom_template_test.rb +8 -0
- data/test/talia_core/active_source_predicate_test.rb +54 -0
- data/test/talia_core/active_source_rdf_test.rb +89 -0
- data/test/talia_core/active_source_test.rb +631 -0
- data/test/talia_core/data_types/data_loader_test.rb +123 -0
- data/test/talia_core/data_types/data_record_test.rb +40 -0
- data/test/talia_core/data_types/file_record_test.rb +171 -0
- data/test/talia_core/data_types/iip_data_test.rb +130 -0
- data/test/talia_core/data_types/image_data_test.rb +88 -0
- data/test/talia_core/data_types/pdf_data_test.rb +68 -0
- data/test/talia_core/data_types/xml_data_test.rb +134 -0
- data/test/talia_core/generic_xml_test.rb +83 -0
- data/test/talia_core/initializer_test.rb +36 -0
- data/test/talia_core/ordered_source_test.rb +398 -0
- data/test/talia_core/rdf_resource_test.rb +115 -0
- data/test/talia_core/semantic_collection_item_test.rb +129 -0
- data/test/talia_core/source_reader_test.rb +33 -0
- data/test/talia_core/source_test.rb +484 -0
- data/test/talia_core/source_transfer_object_test.rb +24 -0
- data/test/talia_core/workflow/publication_workflow_test.rb +242 -0
- data/test/talia_core/workflow/user_class_for_workflow.rb +35 -0
- data/test/talia_core/workflow/workflow_base_test.rb +21 -0
- data/test/talia_core/workflow_test.rb +19 -0
- data/test/talia_util/import_job_helper_test.rb +46 -0
- data/test/test_helper.rb +68 -0
- metadata +262 -0
|
@@ -0,0 +1,151 @@
|
|
|
1
|
+
module TaliaUtil
|
|
2
|
+
|
|
3
|
+
# Test helper mixin for unit tests
|
|
4
|
+
module TestHelpers
|
|
5
|
+
|
|
6
|
+
# Test the types of an element. Asserts if the source has the same types as
|
|
7
|
+
# given in the types argument(s)
|
|
8
|
+
def assert_types(source, *types)
|
|
9
|
+
assert_kind_of(TaliaCore::Source, source) # Just to be sure
|
|
10
|
+
type_list = ""
|
|
11
|
+
source.types.each { |type| type_list << "- Type: #{type.local_name}\n" }
|
|
12
|
+
assert_equal(types.size, source.types.size, "Type size mismatch: Source has #{source.types.size} instead of #{types.size}.\n#{type_list}")
|
|
13
|
+
types.each { |type| assert(source.types.include?(type), "#{source.uri.local_name} should have type #{type}\n#{type_list}") }
|
|
14
|
+
rdf_types = source.my_rdf[N::RDF.type].collect { |type| type.uri.to_s }
|
|
15
|
+
types.each { |type| assert(rdf_types.include?(type.to_s), "#{source.uri.local_name} should have RDF type #{type}\n#{rdf_types}")}
|
|
16
|
+
end
|
|
17
|
+
|
|
18
|
+
# Checks if the given property has the values given to this assertion. If
|
|
19
|
+
# a value is an N::URI, this will assert if the property refers to the
|
|
20
|
+
# Source given by the URI.
|
|
21
|
+
def assert_property(property, *values)
|
|
22
|
+
assert_kind_of(TaliaCore::SemanticCollectionWrapper, property) # Just to be sure
|
|
23
|
+
assert_equal(values.size, property.size, "Expected #{values.size} values instead of #{property.size}")
|
|
24
|
+
property.each do |value|
|
|
25
|
+
assert(values.detect { |val| val.respond_to?(:uri) ? (val.uri.to_s == value.uri.to_s) : (value == val) }, "Found unexpected value #{value}. Value is a #{value.class}\nExpected:\n#{values.join("\n")}")
|
|
26
|
+
end
|
|
27
|
+
end
|
|
28
|
+
|
|
29
|
+
# Creates a dummy Source and saves it
|
|
30
|
+
def make_dummy_source(uri, *types)
|
|
31
|
+
src = TaliaCore::Source.new(uri)
|
|
32
|
+
src.primary_source = true
|
|
33
|
+
types.each do |t|
|
|
34
|
+
TaliaCore::ActiveSource.new(t).save! unless(TaliaCore::ActiveSource.exists?(:uri => t.to_s))
|
|
35
|
+
src.types << t
|
|
36
|
+
end
|
|
37
|
+
src.save!
|
|
38
|
+
return src
|
|
39
|
+
end
|
|
40
|
+
|
|
41
|
+
# Helper to create a variable only once. This should be used from the
|
|
42
|
+
# setup method, and will assign the given block to the given class variable.
|
|
43
|
+
#
|
|
44
|
+
# The block will only be executed once, after that the value for the
|
|
45
|
+
# class variable will be retrieved from a cache.
|
|
46
|
+
#
|
|
47
|
+
# This is a workaround because the Ruby test framework doesn't provide
|
|
48
|
+
# a setup_once method or something like this, and in fact re-creates the
|
|
49
|
+
# Test case object for every single test (go figure). It would be
|
|
50
|
+
# worth switching to RSpec just for this, but it's a heap of work so... the
|
|
51
|
+
# test framework has just the braindead "fixtures" mechanism...
|
|
52
|
+
#
|
|
53
|
+
# The thing is that's a good practice to have reasonably fine-grained tests,
|
|
54
|
+
# and you often have objects that are re-used often, are read-only for all
|
|
55
|
+
# the tests and expensive to create. So you basically want to create them
|
|
56
|
+
# only once.
|
|
57
|
+
#
|
|
58
|
+
# This thing is less than perfect, but it should work for now. Basically it
|
|
59
|
+
# assumes that all tests for a TestCase will be run in a row, and the
|
|
60
|
+
# setup method will execute before the first test and that no other tests
|
|
61
|
+
# will execute before all tests of the TestCase are executed.
|
|
62
|
+
def setup_once(variable, &block)
|
|
63
|
+
variable = variable.to_sym
|
|
64
|
+
value = self.class.obj_cache[variable]
|
|
65
|
+
unless(value)
|
|
66
|
+
value = block.call
|
|
67
|
+
self.class.obj_cache[variable] = value
|
|
68
|
+
end
|
|
69
|
+
assit_not_nil(value)
|
|
70
|
+
value ||= false # We can't have a nil value (will cause the block to re-run)
|
|
71
|
+
instance_variable_set(:"@#{variable}", value)
|
|
72
|
+
end
|
|
73
|
+
|
|
74
|
+
# Creates a source for the given uri
|
|
75
|
+
def create_source(uri)
|
|
76
|
+
TaliaCore::Source.create!(uri)
|
|
77
|
+
end
|
|
78
|
+
|
|
79
|
+
# Assert the given condition is false
|
|
80
|
+
def assert_not(condition, message = nil)
|
|
81
|
+
assert !condition, message
|
|
82
|
+
end
|
|
83
|
+
alias_method :assert_false, :assert_not
|
|
84
|
+
|
|
85
|
+
# Assert the given collection is empty.
|
|
86
|
+
def assert_empty(condition, message = nil)
|
|
87
|
+
assert condition.empty?, message
|
|
88
|
+
end
|
|
89
|
+
|
|
90
|
+
# Assert the given collection is not empty.
|
|
91
|
+
def assert_not_empty(condition, message = nil)
|
|
92
|
+
assert_not condition.empty?, message
|
|
93
|
+
end
|
|
94
|
+
|
|
95
|
+
# Assert the given element is included into the given collection.
|
|
96
|
+
def assert_included(collection, element, message = nil)
|
|
97
|
+
assert collection.include?(element), message
|
|
98
|
+
end
|
|
99
|
+
|
|
100
|
+
# Assert the given object is instance of one of those classes.
|
|
101
|
+
def assert_kind_of_classes(object, *classes)
|
|
102
|
+
assert_included(classes, object.class,
|
|
103
|
+
"#{object} should be instance of one of those classes: #{classes.to_sentence}")
|
|
104
|
+
end
|
|
105
|
+
|
|
106
|
+
# Assert the given object is a boolean.
|
|
107
|
+
def assert_boolean(object)
|
|
108
|
+
assert_kind_of_classes(object, TrueClass, FalseClass)
|
|
109
|
+
end
|
|
110
|
+
|
|
111
|
+
# Assert the source for the given uri exists.
|
|
112
|
+
def assert_source_exist(uri, message = nil)
|
|
113
|
+
assert TaliaCore::Source.exists?(uri), message
|
|
114
|
+
end
|
|
115
|
+
alias_method :assert_source_exists, :assert_source_exist
|
|
116
|
+
end
|
|
117
|
+
end
|
|
118
|
+
|
|
119
|
+
# Add some stuff to the basic test case
|
|
120
|
+
class Test::Unit::TestCase
|
|
121
|
+
include TaliaUtil::TestHelpers
|
|
122
|
+
|
|
123
|
+
protected
|
|
124
|
+
|
|
125
|
+
# Helper variable in the class for setup_once
|
|
126
|
+
def self.obj_cache
|
|
127
|
+
@obj_cache ||= {}
|
|
128
|
+
end
|
|
129
|
+
|
|
130
|
+
# Lets the class suppress the fixtures for the tests
|
|
131
|
+
def self.suppress_fixtures
|
|
132
|
+
@suppress_fixtures = true
|
|
133
|
+
end
|
|
134
|
+
|
|
135
|
+
def self.suppress_fixtures?
|
|
136
|
+
@suppress_fixtures
|
|
137
|
+
end
|
|
138
|
+
|
|
139
|
+
# Adds the possibility to completely disable the fixture mechanism of rails
|
|
140
|
+
if(method_defined?(:setup_with_fixtures) && method_defined?(:teardown_with_fixtures))
|
|
141
|
+
alias_method :setup_with_fixtures_orig, :setup_with_fixtures
|
|
142
|
+
define_method(:setup_with_fixtures) do
|
|
143
|
+
setup_with_fixtures_orig unless(self.class.suppress_fixtures?)
|
|
144
|
+
end
|
|
145
|
+
alias_method :teardown_with_fixtures_orig, :teardown_with_fixtures
|
|
146
|
+
define_method(:teardown_with_fixtures) do
|
|
147
|
+
teardown_with_fixtures_orig unless(self.class.suppress_fixtures?)
|
|
148
|
+
end
|
|
149
|
+
end
|
|
150
|
+
|
|
151
|
+
end
|
|
@@ -0,0 +1,226 @@
|
|
|
1
|
+
# Utility module for tests, rake tasks etc.
|
|
2
|
+
module TaliaUtil
|
|
3
|
+
|
|
4
|
+
# Main utility functions for Talia
|
|
5
|
+
class Util
|
|
6
|
+
class << self
|
|
7
|
+
|
|
8
|
+
# Get the list of files from the "files" option
|
|
9
|
+
def get_files
|
|
10
|
+
puts "Files given: #{ENV['files']}"
|
|
11
|
+
unless(ENV['files'])
|
|
12
|
+
puts("This task needs files to work. Pass them like this files='something/*.x'")
|
|
13
|
+
print_options
|
|
14
|
+
exit(1)
|
|
15
|
+
end
|
|
16
|
+
|
|
17
|
+
FileList.new(ENV['files'])
|
|
18
|
+
end
|
|
19
|
+
|
|
20
|
+
# Get the configured folder for the ontologies
|
|
21
|
+
def ontology_folder
|
|
22
|
+
ENV['ontology_folder'] || File.join(RAILS_ROOT, 'ontologies')
|
|
23
|
+
end
|
|
24
|
+
|
|
25
|
+
# Set up the ontologies from the given folder
|
|
26
|
+
def setup_ontologies
|
|
27
|
+
# Clear the ontologies from RDF, if possible
|
|
28
|
+
adapter = ConnectionPool.write_adapter
|
|
29
|
+
if(adapter.supports_context?)
|
|
30
|
+
TaliaCore::RdfImport.clear_file_contexts
|
|
31
|
+
else
|
|
32
|
+
puts "WARNING: Cannot remove old ontologies, adapter doesn't support contexts."
|
|
33
|
+
end
|
|
34
|
+
|
|
35
|
+
puts "Ontologies loaded from: #{ontology_folder}"
|
|
36
|
+
files = Dir[File.join(ontology_folder, '*.{rdf*,owl}')]
|
|
37
|
+
ENV['rdf_syntax'] ||= 'rdfxml'
|
|
38
|
+
params = [ENV['rdf_syntax'], files]
|
|
39
|
+
params << :auto if(adapter.supports_context?)
|
|
40
|
+
TaliaCore::RdfImport::import(*params)
|
|
41
|
+
RdfUpdate::owl_to_rdfs
|
|
42
|
+
end
|
|
43
|
+
|
|
44
|
+
# Init the talia core system
|
|
45
|
+
def init_talia
|
|
46
|
+
return if(TaliaCore::Initializer.initialized)
|
|
47
|
+
|
|
48
|
+
# If options are not set, the initializer will fall back to the internal default
|
|
49
|
+
TaliaCore::Initializer.talia_root = ENV['talia_root']
|
|
50
|
+
TaliaCore::Initializer.environment = ENV['environment']
|
|
51
|
+
|
|
52
|
+
config_file = ENV['config'] ? ENV['config'] : 'talia_core'
|
|
53
|
+
|
|
54
|
+
# run the initializer
|
|
55
|
+
TaliaCore::Initializer.run(config_file) do |config|
|
|
56
|
+
unless(flag?('no_standalone'))
|
|
57
|
+
puts "Always using standalone db from utilities."
|
|
58
|
+
puts "Give the no_standalone option to override it."
|
|
59
|
+
config['standalone_db'] = "true"
|
|
60
|
+
end
|
|
61
|
+
end
|
|
62
|
+
|
|
63
|
+
puts("\nTaliaCore initialized")
|
|
64
|
+
|
|
65
|
+
# # Flush the database if requested
|
|
66
|
+
if(flag?('reset_db'))
|
|
67
|
+
flush_db
|
|
68
|
+
puts "DB flushed"
|
|
69
|
+
end
|
|
70
|
+
|
|
71
|
+
# Flus the rdf if requested
|
|
72
|
+
if(flag?('reset_rdf'))
|
|
73
|
+
flush_rdf
|
|
74
|
+
puts "RDF flushed"
|
|
75
|
+
end
|
|
76
|
+
end
|
|
77
|
+
|
|
78
|
+
# Get info from the Talia configuraion
|
|
79
|
+
def talia_config
|
|
80
|
+
puts "Talia configuration"
|
|
81
|
+
puts ""
|
|
82
|
+
puts "TALIA_ROOT: #{TALIA_ROOT}"
|
|
83
|
+
puts "Environment: #{TaliaCore::CONFIG['environment']}"
|
|
84
|
+
puts "Standalone DB: #{TaliaCore::CONFIG['standalone_db']}"
|
|
85
|
+
puts "Data Directory: #{TaliaCore::CONFIG['data_directory_location']}"
|
|
86
|
+
puts "Local Domain: #{N::LOCAL}"
|
|
87
|
+
end
|
|
88
|
+
|
|
89
|
+
# Put the title for Talia
|
|
90
|
+
def title
|
|
91
|
+
puts "\nTalia Digital Library system. Version: #{TaliaCore::Version::STRING}"
|
|
92
|
+
puts "http://www.talia.discovery-project.eu/\n\n"
|
|
93
|
+
end
|
|
94
|
+
|
|
95
|
+
# Flush the database. This only flushes the main data tables!
|
|
96
|
+
def flush_db
|
|
97
|
+
[ 'active_sources', 'data_records', 'semantic_properties', 'semantic_relations'].reverse.each { |f| ActiveRecord::Base.connection.execute "DELETE FROM #{f}" }
|
|
98
|
+
# Also remove the "unsaved cache" for the wrappers (may be important during testing)
|
|
99
|
+
TaliaCore::SemanticCollectionWrapper.instance_variable_set(:'@unsaved_source_cache', {})
|
|
100
|
+
end
|
|
101
|
+
|
|
102
|
+
# Flush the RDF store
|
|
103
|
+
def flush_rdf
|
|
104
|
+
ConnectionPool.write_adapter.clear
|
|
105
|
+
end
|
|
106
|
+
|
|
107
|
+
# Remove the data directories
|
|
108
|
+
def clear_data
|
|
109
|
+
data_dir = TaliaCore::CONFIG['data_directory_location']
|
|
110
|
+
iip_dir = TaliaCore::CONFIG['iip_root_directory_location']
|
|
111
|
+
FileUtils.rm_rf(data_dir) if(File.exist?(data_dir))
|
|
112
|
+
FileUtils.rm_rf(iip_dir) if(File.exist?(iip_dir))
|
|
113
|
+
end
|
|
114
|
+
|
|
115
|
+
|
|
116
|
+
# Do a full reset of the data store
|
|
117
|
+
def full_reset
|
|
118
|
+
flush_db
|
|
119
|
+
flush_rdf
|
|
120
|
+
clear_data
|
|
121
|
+
setup_ontologies
|
|
122
|
+
end
|
|
123
|
+
|
|
124
|
+
# Rewrite the RDF for the whole database. Will yield without parameters
|
|
125
|
+
# for progress-reporting blocks.
|
|
126
|
+
# FIXME: At the moment, this
|
|
127
|
+
# looses all RDF data that is not in the database.
|
|
128
|
+
def rewrite_rdf
|
|
129
|
+
flush_rdf
|
|
130
|
+
# We'll get all data from single query.
|
|
131
|
+
fat_rels = TaliaCore::SemanticRelation.find(:all, :joins => fat_record_joins,
|
|
132
|
+
:select => fat_record_select)
|
|
133
|
+
fat_rels.each do |rec|
|
|
134
|
+
subject = N::URI.new(rec.subject_uri)
|
|
135
|
+
predicate = N::URI.new(rec.predicate_uri)
|
|
136
|
+
object = if(rec.object_uri)
|
|
137
|
+
N::URI.new(rec.object_uri)
|
|
138
|
+
else
|
|
139
|
+
rec.property_value
|
|
140
|
+
end
|
|
141
|
+
FederationManager.add(subject, predicate, object)
|
|
142
|
+
yield if(block_given?)
|
|
143
|
+
end
|
|
144
|
+
|
|
145
|
+
# Rewriting all the "runtime type" rdf triples
|
|
146
|
+
# We'll select the type as something else, so that it doesn't try to do
|
|
147
|
+
# STI instantiation (which would cause this to blow for classes that
|
|
148
|
+
# are defined outside the core.
|
|
149
|
+
TaliaCore::ActiveSource.find(:all, :select => 'uri, type AS runtime_type').each do |src|
|
|
150
|
+
type = (src.runtime_type || 'ActiveSource')
|
|
151
|
+
FederationManager.add(src, N::RDF.type, N::TALIA + type)
|
|
152
|
+
yield if(block_given?)
|
|
153
|
+
end
|
|
154
|
+
end
|
|
155
|
+
|
|
156
|
+
# This gives the number of triples that would be rewritten on #rewrite_rdf
|
|
157
|
+
def rewrite_count
|
|
158
|
+
TaliaCore::SemanticRelation.count + TaliaCore::ActiveSource.count
|
|
159
|
+
end
|
|
160
|
+
|
|
161
|
+
# Load the fixtures
|
|
162
|
+
def load_fixtures
|
|
163
|
+
# fixtures = ENV['FIXTURES'] ? ENV['FIXTURES'].split(/,/) : Dir.glob(File.join(File.dirname(__FILE__), 'test', 'fixtures', '*.{yml,csv}'))
|
|
164
|
+
fixtures = [ 'active_sources', 'semantic_relations', 'semantic_properties' 'data_records']
|
|
165
|
+
fixtures.reverse.each { |f| ActiveRecord::Base.connection.execute "DELETE FROM #{f}" }
|
|
166
|
+
fixtures.each do |fixture_file|
|
|
167
|
+
Fixtures.create_fixtures(File.join('test', 'fixtures'), File.basename(fixture_file, '.*'))
|
|
168
|
+
end
|
|
169
|
+
end
|
|
170
|
+
|
|
171
|
+
# Do migrations
|
|
172
|
+
def do_migrations
|
|
173
|
+
migration_path = File.join("generators", "talia", "templates", "migrations")
|
|
174
|
+
ActiveRecord::Migrator.migrate(migration_path, ENV["VERSION"] ? ENV["VERSION"].to_i : nil )
|
|
175
|
+
end
|
|
176
|
+
|
|
177
|
+
# Check if the given flag is set on the command line
|
|
178
|
+
def flag?(the_flag)
|
|
179
|
+
assit_not_nil(the_flag)
|
|
180
|
+
ENV[the_flag] && (ENV[the_flag] == "yes" || ENV[the_flag] == "true")
|
|
181
|
+
end
|
|
182
|
+
|
|
183
|
+
# For selecting "fat" records on the semantic properties, including the
|
|
184
|
+
# objects. Used for rewriting the rdf. TODO: Review after merging
|
|
185
|
+
# with optimized branch
|
|
186
|
+
def fat_record_select
|
|
187
|
+
select = 'semantic_relations.id AS id, semantic_relations.created_at AS created_at, '
|
|
188
|
+
select << 'semantic_relations.updated_at AS updated_at, '
|
|
189
|
+
select << 'object_id, object_type, subject_id, predicate_uri, '
|
|
190
|
+
select << 'obj_props.created_at AS property_created_at, '
|
|
191
|
+
select << 'obj_props.updated_at AS property_updated_at, '
|
|
192
|
+
select << 'obj_props.value AS property_value, '
|
|
193
|
+
select << 'obj_sources.created_at AS object_created_at, '
|
|
194
|
+
select << 'obj_sources.updated_at AS object_updated_at, obj_sources.type AS object_realtype, '
|
|
195
|
+
select << 'obj_sources.uri AS object_uri, '
|
|
196
|
+
select << 'subject_sources.uri AS subject_uri'
|
|
197
|
+
select
|
|
198
|
+
end
|
|
199
|
+
|
|
200
|
+
# Select semantic properties joined with all connected tables.
|
|
201
|
+
# TODO: Review after merging with optimized branch
|
|
202
|
+
def fat_record_joins
|
|
203
|
+
joins = " LEFT JOIN active_sources AS obj_sources ON semantic_relations.object_id = obj_sources.id AND semantic_relations.object_type = 'TaliaCore::ActiveSource'"
|
|
204
|
+
joins << " LEFT JOIN semantic_properties AS obj_props ON semantic_relations.object_id = obj_props.id AND semantic_relations.object_type = 'TaliaCore::SemanticProperty'"
|
|
205
|
+
joins << " LEFT JOIN active_sources AS subject_sources ON semantic_relations.subject_id = subject_sources.id"
|
|
206
|
+
joins
|
|
207
|
+
end
|
|
208
|
+
|
|
209
|
+
# print the common options for the tasks
|
|
210
|
+
def print_options
|
|
211
|
+
puts "\nGeneral options (not all options are valid for all tasks):"
|
|
212
|
+
puts "files=<pattern> - Files for the task (a pattern to match the files)"
|
|
213
|
+
puts "talia_root=<path> - Manually configure the TALIA_ROOT path"
|
|
214
|
+
puts " (default:autodetect)"
|
|
215
|
+
puts "reset_rdf={yes|no} - Flush the RDF store (default:no)"
|
|
216
|
+
puts "reset_db={yes|no} - Flush the database (default:no)"
|
|
217
|
+
puts "config=<filename> - Talia configuration file (default: talia_core)"
|
|
218
|
+
puts "environment=<env> - Environment for configuration (default: development)"
|
|
219
|
+
puts "data_dir=<dir> - Directory for the data files"
|
|
220
|
+
puts "verbose={yes|no} - Show some additional info"
|
|
221
|
+
puts ""
|
|
222
|
+
end
|
|
223
|
+
|
|
224
|
+
end
|
|
225
|
+
end
|
|
226
|
+
end
|
|
@@ -0,0 +1,80 @@
|
|
|
1
|
+
module TaliaUtil
|
|
2
|
+
|
|
3
|
+
# Import module for Talia data contained in YAML files
|
|
4
|
+
class YamlImport
|
|
5
|
+
class << self
|
|
6
|
+
|
|
7
|
+
# Register the namespaces define in the data file
|
|
8
|
+
def register_namespaces(data)
|
|
9
|
+
if(data["namespaces"])
|
|
10
|
+
data["namespaces"].each do |shortcut, uri|
|
|
11
|
+
if(N::URI.shortcut_exists?(shortcut))
|
|
12
|
+
if(!N::URI[shortcut].to_s == shortcut)
|
|
13
|
+
puts "WARNING: Namespace for #{shortcut} already registered with #{N::URI[shortcut]} instead of #{uri}."
|
|
14
|
+
else
|
|
15
|
+
puts "Namespace #{shortcut} already registered."
|
|
16
|
+
end
|
|
17
|
+
else
|
|
18
|
+
N::Namespace.shortcut(shortcut, uri)
|
|
19
|
+
puts "Registered namespace #{shortcut} for #{uri}"
|
|
20
|
+
end
|
|
21
|
+
end
|
|
22
|
+
data.delete("namespaces")
|
|
23
|
+
end
|
|
24
|
+
end
|
|
25
|
+
|
|
26
|
+
# Process multiple YAML files
|
|
27
|
+
def import_multi_files(files)
|
|
28
|
+
files.each do |file|
|
|
29
|
+
import_file(file)
|
|
30
|
+
end
|
|
31
|
+
end
|
|
32
|
+
|
|
33
|
+
# Import the data from a YAML file
|
|
34
|
+
def import_file(datafile)
|
|
35
|
+
data = YAML::load(File.open(datafile))
|
|
36
|
+
|
|
37
|
+
register_namespaces(data)
|
|
38
|
+
|
|
39
|
+
progress = ProgressBar.new("Importing", data.size)
|
|
40
|
+
|
|
41
|
+
puts "Importing data from #{datafile}..."
|
|
42
|
+
|
|
43
|
+
data.each do |source_name, data_set|
|
|
44
|
+
puts "Processing #{source_name}" if(Util::flag?("verbose"))
|
|
45
|
+
primary_source = (data_set.delete("primary_source") == "true") ? 'true' : 'false'
|
|
46
|
+
types = data_set.delete("type")
|
|
47
|
+
types = [types] unless(types.kind_of?(Array))
|
|
48
|
+
types.compact!
|
|
49
|
+
# Create the type uris
|
|
50
|
+
types = types.collect { |type| N::URI.make_uri(type) }
|
|
51
|
+
|
|
52
|
+
# Create the source
|
|
53
|
+
source = TaliaCore::Source.new(source_name)
|
|
54
|
+
source.talias::primary_source << primary_source ? 'true' : 'false'
|
|
55
|
+
source.types << types
|
|
56
|
+
source.save! # save the thing
|
|
57
|
+
|
|
58
|
+
# Now add the rdf elements
|
|
59
|
+
data_set.each do |name, value|
|
|
60
|
+
uri = N::URI.make_uri(name, "#")
|
|
61
|
+
value = [value] unless(value.kind_of?(Array))
|
|
62
|
+
|
|
63
|
+
value.each do |val|
|
|
64
|
+
val = TaliaCore::Source.new(N::URI.make_uri(val)) if(val.index(":"))
|
|
65
|
+
source[uri] << val
|
|
66
|
+
end
|
|
67
|
+
end
|
|
68
|
+
|
|
69
|
+
source.save! # Save all
|
|
70
|
+
|
|
71
|
+
progress.inc
|
|
72
|
+
end
|
|
73
|
+
|
|
74
|
+
progress.finish
|
|
75
|
+
puts "Done"
|
|
76
|
+
end
|
|
77
|
+
end
|
|
78
|
+
end
|
|
79
|
+
end
|
|
80
|
+
|
data/lib/talia_util.rb
ADDED
|
@@ -0,0 +1,13 @@
|
|
|
1
|
+
# TaliaCore loader
|
|
2
|
+
require File.join(File.dirname(__FILE__), 'talia_dependencies')
|
|
3
|
+
|
|
4
|
+
require 'core_ext'
|
|
5
|
+
require 'talia_util/data_import'
|
|
6
|
+
require 'talia_core/rdf_import'
|
|
7
|
+
require 'talia_util/yaml_import'
|
|
8
|
+
require 'talia_util/rdf_update'
|
|
9
|
+
require 'talia_util/progressbar'
|
|
10
|
+
|
|
11
|
+
# Stuff we just load from the gems
|
|
12
|
+
gem "builder"
|
|
13
|
+
require "builder"
|
data/lib/user.rb
ADDED
|
@@ -0,0 +1,116 @@
|
|
|
1
|
+
require 'digest/sha1'
|
|
2
|
+
class User < ActiveRecord::Base
|
|
3
|
+
include ActsAsRoled
|
|
4
|
+
has_and_belongs_to_many :roles
|
|
5
|
+
attr_accessor :roles_attributes
|
|
6
|
+
attr_accessible :roles_attributes
|
|
7
|
+
after_update :save_roles
|
|
8
|
+
|
|
9
|
+
# authorized_as? simply needs to return true or false whether a user has a role or not.
|
|
10
|
+
# It may be a good idea to have "admin" roles return true always
|
|
11
|
+
def authorized_as?(role_name)
|
|
12
|
+
return true if role_names.include?("admin")
|
|
13
|
+
has_role?(role_name)
|
|
14
|
+
end
|
|
15
|
+
|
|
16
|
+
def has_role?(role_name)
|
|
17
|
+
role_names.include? role_name.to_s
|
|
18
|
+
end
|
|
19
|
+
|
|
20
|
+
def roles_to_sentence
|
|
21
|
+
role_names.to_sentence
|
|
22
|
+
end
|
|
23
|
+
|
|
24
|
+
# Virtual attribute for the unencrypted password
|
|
25
|
+
attr_accessor :password
|
|
26
|
+
|
|
27
|
+
validates_presence_of :login, :email
|
|
28
|
+
validates_presence_of :password, :if => :password_required?
|
|
29
|
+
validates_presence_of :password_confirmation, :if => :password_required?
|
|
30
|
+
validates_length_of :password, :within => 4..40, :if => :password_required?
|
|
31
|
+
validates_confirmation_of :password, :if => :password_required?
|
|
32
|
+
validates_length_of :login, :within => 3..40
|
|
33
|
+
validates_length_of :email, :within => 3..100
|
|
34
|
+
validates_uniqueness_of :login, :email, :case_sensitive => false
|
|
35
|
+
before_save :encrypt_password, :normalize_open_id
|
|
36
|
+
|
|
37
|
+
# prevents a user from submitting a crafted form that bypasses activation
|
|
38
|
+
# anything else you want your user to change should be added here.
|
|
39
|
+
attr_accessible :login, :email, :password, :password_confirmation, :open_id
|
|
40
|
+
|
|
41
|
+
# Authenticates a user by their login name and unencrypted password. Returns the user or nil.
|
|
42
|
+
def self.authenticate(login, password)
|
|
43
|
+
u = find_by_login(login) # need to get the salt
|
|
44
|
+
u && u.authenticated?(password) ? u : nil
|
|
45
|
+
end
|
|
46
|
+
|
|
47
|
+
# Authenticates a user by their open id indentifier. Returns the user or nil.
|
|
48
|
+
def self.open_id_authentication(identity_url)
|
|
49
|
+
u = find_by_open_id(identity_url) # need to get the salt
|
|
50
|
+
u ? u : nil
|
|
51
|
+
end
|
|
52
|
+
|
|
53
|
+
# Encrypts some data with the salt.
|
|
54
|
+
def self.encrypt(password, salt)
|
|
55
|
+
Digest::SHA1.hexdigest("--#{salt}--#{password}--")
|
|
56
|
+
end
|
|
57
|
+
|
|
58
|
+
# Encrypts the password with the user salt
|
|
59
|
+
def encrypt(password)
|
|
60
|
+
self.class.encrypt(password, salt)
|
|
61
|
+
end
|
|
62
|
+
|
|
63
|
+
def authenticated?(password)
|
|
64
|
+
crypted_password == encrypt(password)
|
|
65
|
+
end
|
|
66
|
+
|
|
67
|
+
def remember_token?
|
|
68
|
+
remember_token_expires_at && Time.now.utc < remember_token_expires_at
|
|
69
|
+
end
|
|
70
|
+
|
|
71
|
+
# These create and unset the fields required for remembering users between browser closes
|
|
72
|
+
def remember_me
|
|
73
|
+
remember_me_for 2.weeks
|
|
74
|
+
end
|
|
75
|
+
|
|
76
|
+
def remember_me_for(time)
|
|
77
|
+
remember_me_until time.from_now.utc
|
|
78
|
+
end
|
|
79
|
+
|
|
80
|
+
def remember_me_until(time)
|
|
81
|
+
self.remember_token_expires_at = time
|
|
82
|
+
self.remember_token = encrypt("#{email}--#{remember_token_expires_at}")
|
|
83
|
+
save(false)
|
|
84
|
+
end
|
|
85
|
+
|
|
86
|
+
def forget_me
|
|
87
|
+
self.remember_token_expires_at = nil
|
|
88
|
+
self.remember_token = nil
|
|
89
|
+
save(false)
|
|
90
|
+
end
|
|
91
|
+
|
|
92
|
+
protected
|
|
93
|
+
# before filter
|
|
94
|
+
def encrypt_password
|
|
95
|
+
return if password.blank?
|
|
96
|
+
self.salt = Digest::SHA1.hexdigest("--#{Time.now.to_s}--#{login}--") if new_record?
|
|
97
|
+
self.crypted_password = encrypt(password)
|
|
98
|
+
end
|
|
99
|
+
|
|
100
|
+
def normalize_open_id
|
|
101
|
+
self.open_id = OpenIdAuthentication.normalize_url(open_id) unless open_id.blank?
|
|
102
|
+
end
|
|
103
|
+
|
|
104
|
+
def password_required?
|
|
105
|
+
crypted_password.blank? || !password.blank?
|
|
106
|
+
end
|
|
107
|
+
|
|
108
|
+
def role_names
|
|
109
|
+
@role_names ||= self.roles.map(&:name)
|
|
110
|
+
end
|
|
111
|
+
|
|
112
|
+
def save_roles
|
|
113
|
+
return if roles_attributes.nil?
|
|
114
|
+
self.roles = Role.find_by_names(roles_attributes)
|
|
115
|
+
end
|
|
116
|
+
end
|
data/lib/version.rb
ADDED
|
@@ -0,0 +1,15 @@
|
|
|
1
|
+
require 'yaml'
|
|
2
|
+
|
|
3
|
+
module TaliaCore #:nodoc:
|
|
4
|
+
module Version #:nodoc:
|
|
5
|
+
|
|
6
|
+
version = YAML.load_file(File.join(File.dirname(__FILE__), '..', 'VERSION.yml'))
|
|
7
|
+
|
|
8
|
+
MAJOR = version[:major]
|
|
9
|
+
MINOR = version[:minor]
|
|
10
|
+
TINY = version[:patch]
|
|
11
|
+
|
|
12
|
+
STRING = [ MAJOR, MINOR, TINY ].join(".")
|
|
13
|
+
|
|
14
|
+
end
|
|
15
|
+
end
|
|
@@ -0,0 +1,11 @@
|
|
|
1
|
+
require File.join(File.dirname(__FILE__), '..', 'test_helper')
|
|
2
|
+
require File.join(File.dirname(__FILE__), '..', '..', 'lib', 'core_ext', 'string')
|
|
3
|
+
|
|
4
|
+
class StringTest < Test::Unit::TestCase
|
|
5
|
+
def test_to_permalink
|
|
6
|
+
assert_equal('Should_Strip_All_Non_Word_Chars', 'should strip *all* non-word chars!'.to_permalink)
|
|
7
|
+
assert_equal('Should_Strip_White_Spaces', 'should strip white spaces'.to_permalink)
|
|
8
|
+
assert_equal('Should_Titleize_Mixed_Case_Strings', 'sHoULD tItLEIzE mIxEd cAsE sTrINgS'.to_permalink)
|
|
9
|
+
assert_equal('Should_Replace_Spaces_With_Underscores', 'should replace spaces with underscores'.to_permalink)
|
|
10
|
+
end
|
|
11
|
+
end
|
|
@@ -0,0 +1,54 @@
|
|
|
1
|
+
# Load the helper class
|
|
2
|
+
require File.join(File.dirname(__FILE__), '..', 'test_helper')
|
|
3
|
+
|
|
4
|
+
module TaliaCore
|
|
5
|
+
|
|
6
|
+
# Test the ActiveSource
|
|
7
|
+
class ActiveSourcePredicateTest < Test::Unit::TestCase
|
|
8
|
+
|
|
9
|
+
def setup
|
|
10
|
+
setup_once(:flush) do
|
|
11
|
+
TaliaUtil::Util.flush_rdf
|
|
12
|
+
TaliaUtil::Util.flush_db
|
|
13
|
+
true
|
|
14
|
+
end
|
|
15
|
+
end
|
|
16
|
+
|
|
17
|
+
def test_each_cached
|
|
18
|
+
src = ActiveSource.new('http://pred_test/each_cached')
|
|
19
|
+
src[N::RDF.rew] << 'value'
|
|
20
|
+
cached = []
|
|
21
|
+
src.each_cached_wrapper do |w|
|
|
22
|
+
cached << w
|
|
23
|
+
end
|
|
24
|
+
assert_equal(1, cached.size)
|
|
25
|
+
end
|
|
26
|
+
|
|
27
|
+
def test_cached_predicate
|
|
28
|
+
src = ActiveSource.new('http://pred_test/cached_predicate')
|
|
29
|
+
src[N::RDF.rew] << 'value'
|
|
30
|
+
# We assume that the cached thing is now in the internal structure
|
|
31
|
+
w = src.instance_variable_get(:@type_cache)[N::RDF.rew.to_s]
|
|
32
|
+
items = w.instance_variable_get(:@items)
|
|
33
|
+
assert_kind_of(Array, items)
|
|
34
|
+
assert_equal(['value'], items.collect { |i| i.value })
|
|
35
|
+
assert_same(src[N::RDF.rew], w)
|
|
36
|
+
end
|
|
37
|
+
|
|
38
|
+
def test_cached_after_save
|
|
39
|
+
src = ActiveSource.new('http://pred_test/cached_after_save')
|
|
40
|
+
src[N::RDF.rew] << 'value'
|
|
41
|
+
src.save!
|
|
42
|
+
# We assume that the cached thing is now in the internal structure
|
|
43
|
+
w = src.instance_variable_get(:@type_cache)[N::RDF.rew.to_s]
|
|
44
|
+
items = w.send(:items) # This should correctly reload the items
|
|
45
|
+
assert_kind_of(Array, items)
|
|
46
|
+
assert_equal(['value'], items.collect { |i| i.value })
|
|
47
|
+
assert_same(src[N::RDF.rew], w)
|
|
48
|
+
# Check if the RDF was updated. The RDF must be updated from the cached wrappers
|
|
49
|
+
# before the wrappers are saved themselves
|
|
50
|
+
assert_equal(['value'], src.my_rdf[N::RDF.rew], "Mismatch of the RDF, maybe the callbacks in wrong order?")
|
|
51
|
+
end
|
|
52
|
+
|
|
53
|
+
end
|
|
54
|
+
end
|