sqlbible 1.0.1 → 1.2.0

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
checksums.yaml CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: '066989f0d6675a25e650331321207e088e1ad798518020ccaa3745b7e56faf1b'
4
- data.tar.gz: fd47a661496035fedeca803311e80c83eb8a4d2211695d7ad6049c7b00648320
3
+ metadata.gz: b620e9b57b9ffdc57b71231b5a6bfb0619dd196dd99428a4f3ab71d682f60b72
4
+ data.tar.gz: 196e6a8907ab5b90adce9d9d2c935593796e9b86eb6b7d362a0ca419436b76ad
5
5
  SHA512:
6
- metadata.gz: 27e852c018052bfe6f5d00a185ce22ffa746b80b3a8b4857968d4bf740a5ad4eaf0e0d140a0da6ad66637518e5f6384c53d8d0da04ef65f40488fea928dd4b95
7
- data.tar.gz: b7904cc0c6891a437d65a3e609296dd183b7aa22ad001dbb87f74079f133142052b8552f85b0e88e373996d4baf3c163a600634229580751484e579a0d36e328
6
+ metadata.gz: 2ac874cb85c60996f406f522f6d010e9e6c07c950b10ed1d9783a87ac936bc1ddc8123dc382ae92298e15382962faed773c2b43b4e6a35e4787e06a3183c5e58
7
+ data.tar.gz: 927964e349b1e54f5156b3e994ef704411ed5845a0c7c13edabe175170a2d759801525438e1459c76598100159f7e7b8b07d13f39f6043edc5872f71bfa22261
data/README.md CHANGED
@@ -19,7 +19,7 @@ bible = Sqlbible.new('kjv.sqlite')
19
19
  # simple search
20
20
  bible.search(/Jesus/)
21
21
 
22
- # Sqlbible is designed to use well with Scripref references and passages
22
+ # Sqlbible is designed to work well with Scripref references and passages
23
23
  require 'scripref'
24
24
 
25
25
  # define a reference for the gospels
@@ -35,6 +35,9 @@ bible.reference(ref)
35
35
 
36
36
  ### Sqlbible as command-line application
37
37
 
38
+ It is possible to convert bibles in OSIS XML format to SQLite databases for
39
+ Sqlbible, to search for regular expressions and show text for references.
40
+
38
41
  See help of the command-line application:
39
42
 
40
43
  ```shell
data/bin/sqlbible CHANGED
@@ -2,18 +2,103 @@
2
2
  # encoding: utf-8
3
3
  # frozen_string_literal: false
4
4
 
5
- require 'optimist'
5
+ require 'optimist_xl'
6
+ require 'scripref'
7
+ require 'sqlbible'
6
8
 
7
- opts = Optimist.options do
8
- opt :convert, 'Convert a bible from OSIS-XML to Sqlbible format', type: String
9
+ result = OptimistXL.options do
10
+ synopsis 'Usage: sqlbible [options] [<command> [suboptions] <filename>]'
11
+ subcmd :convert, 'Convert a bible from OSIS-XML to Sqlbible format' do
12
+ opt :name, 'Name of the converted bible module or output filename of the generated .sqlbible file', type: String, required: true
13
+ opt :overwrite, 'Overwrite existing module or output file if exist', type: :Boolean, default: false
14
+ end
15
+ subcmd :search, 'Search with regular expressions' do
16
+ opt :name, 'Name of the bible module filename of an .sqlbible file', type: String
17
+ opt :search, 'Regular expression to search (multiple allowed)', type: String, multi: true, required: true
18
+ opt :lang, 'Language for parsing and formatting scripture references', type: String, permitted: %w(de en), default: 'en'
19
+ opt :output, 'Output filename', type: String
20
+ opt :range, 'Search range, example: "John 1-10"', type: String
21
+ end
22
+ subcmd :text, 'Show text of references' do
23
+ opt :name, 'Name of the bible module filename of an .sqlbible file', type: String
24
+ opt :lang, 'Language for parsing and formatting scripture references', type: String, permitted: %w(de en), default: 'en'
25
+ opt :output, 'Output filename', type: String
26
+ opt :reference, 'Reference to show, example: "John 3:16; 10:27-30"', type: String, required: true
27
+ end
28
+ version format("sqlbible %s\nschema version %s", Sqlbible::VERSION, Sqlbible.schema_version)
29
+ end
30
+
31
+ def determine_lang_mod subopts
32
+ case l = subopts[:lang]
33
+ when 'en', nil
34
+ Scripref::English
35
+ when 'de'
36
+ Scripref::German
37
+ else
38
+ fail format("lang option #{l} is not supported")
39
+ end
9
40
  end
10
41
 
11
- if osis_fn = opts[:convert]
42
+ def determine_out subopts
43
+ if fn = subopts[:output]
44
+ out = File.open(opts[:output], 'w')
45
+ else
46
+ out = $stdout
47
+ end
48
+ end
49
+
50
+ def format_verse f, v
51
+ format('%s: %s', f.format(v.scripref_passage), v.plaintext)
52
+ end
53
+
54
+ subopts = result.subcommand_options
55
+
56
+ case result.subcommand
57
+ when 'convert'
58
+ require 'fileutils'
12
59
  require 'sqlbible/convert'
13
- sqlite_fn = osis_fn.sub(/\.xml/i, '') << '.sqlite'
60
+ unless osis_fn = result.leftovers.first
61
+ $stderr.puts 'no filename given'
62
+ exit 1
63
+ end
64
+ sqlbible_fn = Sqlbible.resolve_db_filename(subopts[:name])
65
+ if !subopts[:overwrite] && File.exist?(sqlbible_fn)
66
+ $stderr.puts format('file %s exist, conversion aborted', sqlbible_fn)
67
+ exit 1
68
+ end
69
+ unless File.exist?(dir = Sqlbible.bibles_dir)
70
+ puts format('create directory %s', dir)
71
+ FileUtils.mkdir_p dir
72
+ end
14
73
  if $stdout.tty?
15
- puts "convert #{osis_fn} to #{sqlite_fn} ..."
74
+ puts "convert #{osis_fn} to #{sqlbible_fn} ..."
75
+ end
76
+ Sqlbible.convert osis_fn, sqlbible_fn
77
+ exit
78
+ when 'search'
79
+ searches = subopts[:search]
80
+ lang_mod = determine_lang_mod(subopts)
81
+ if r = subopts[:range]
82
+ p = Scripref::Parser.new(lang_mod)
83
+ range = p.parse(r)
84
+ else
85
+ range = nil
86
+ end
87
+ out = determine_out(subopts)
88
+ bible = Sqlbible.new(subopts[:name])
89
+ regexes = searches.map {|s| Regexp.new(s)}
90
+ f = Scripref::Formatter.new(lang_mod, bookformat: :abbrev)
91
+ bible.search(regexes, range: range).each do |v|
92
+ out.puts format_verse(f, v)
93
+ end
94
+ when 'text'
95
+ lang_mod = determine_lang_mod(subopts)
96
+ p = Scripref::Parser.new(lang_mod)
97
+ f = Scripref::Formatter.new(lang_mod, bookformat: :abbrev)
98
+ ref = p.parse(subopts[:reference])
99
+ bible = Sqlbible.new(subopts[:name])
100
+ out = determine_out subopts
101
+ bible.reference(ref).flatten.each do |v|
102
+ out.puts format_verse(f, v)
16
103
  end
17
- Sqlbible.convert osis_fn, sqlite_fn
18
104
  end
19
-
@@ -8,6 +8,8 @@ require_relative '../sqlbible'
8
8
 
9
9
  class Sqlbible
10
10
 
11
+ # Convert a bible file in OSIS XML format to another file in SQLite format
12
+ # for Sqlbible
11
13
  def self.convert osis_fn, sqlite_fn
12
14
  last_bookid = nil
13
15
  booknumber = 0
@@ -0,0 +1,6 @@
1
+ # encoding: utf-8
2
+ # frozen_string_literal: true
3
+
4
+ class Sqlbible
5
+ VERSION = '1.2.0'
6
+ end
data/lib/sqlbible.rb CHANGED
@@ -1,76 +1,127 @@
1
- # encooding: utf-8
1
+ # encoding: utf-8
2
2
  # frozen_string_literal: true
3
3
 
4
4
  require 'scripref'
5
5
  require 'sqlite3'
6
6
 
7
+ require_relative 'sqlbible/version'
8
+
7
9
  class Sqlbible
8
10
 
9
- VERSION = '1.0.1'
11
+ attr_reader :db_filename
10
12
 
11
- def initialize db_filename
12
- @db = SQLite3::Database.new(db_filename)
13
+ def initialize db_name
14
+ @db_filename = Sqlbible.resolve_db_filename(db_name)
15
+ unless File.exist? @db_filename
16
+ fail ArgumentError, format('database %s not found, file %s does not exist', db_name, @db_filename)
17
+ end
18
+ @db = SQLite3::Database.new(@db_filename)
13
19
  @db.enable_load_extension(true)
14
20
  pcre_extension_file = ENV['SQLITE_PCRE_EXTENSION']
15
21
  @db.load_extension(pcre_extension_file) if pcre_extension_file
16
22
  check_schema_version
17
23
  end
18
24
 
25
+ # Get an array of Verse instances for a Scripref::Passage
19
26
  def passage pass
20
27
  rowid1, rowid2 = passage2rowids(pass)
21
28
  res = select_text(where: 'rowid between ? and ?', args: [rowid1, rowid2])
22
29
  parse_verse_list(res)
23
30
  end
24
31
 
32
+ # Get an array of arrays of Verse instances for a Scripref reference (array
33
+ # of Scripref::Passage instances)
25
34
  def reference ref
26
35
  ref.select {|e| e.kind_of?(Scripref::Passage)}.map {|pass| passage(pass)}
27
36
  end
28
37
 
29
- def search obj, range: nil
38
+ # Get an array of Verse instances for a search with one ore more regular
39
+ # expressions (optional a search range of a Scripref reference is possible)
40
+ def search *searches, range: nil
30
41
  where_arr = []
31
42
  args = []
32
43
  if range
33
44
  passages = Array(range).select {|e| e.kind_of? Scripref::Passage}
34
45
  passages.size.times {where_arr << 'rowid between ? and ?'}
35
- where_arr == [or_join_where(where_arr)]
46
+ where_arr = [or_join_where(where_arr)]
36
47
  args = passages.map {|p| passage2rowids(p)}.flatten
37
48
  end
38
- case obj
39
- when Regexp
40
- where_arr << 'plaintext regexp ?'
41
- args << obj.to_s
42
- res = select_text(where: and_join_where(where_arr), args: args)
43
- else
44
- fail 'unknown search object'
49
+ searches.flatten.each do |o|
50
+ case o
51
+ when Regexp
52
+ where_arr << 'plaintext regexp ?'
53
+ args << o.to_s
54
+ else
55
+ fail format('search objects of class %s are not (yet) supported', o.class)
56
+ end
45
57
  end
58
+ where = and_join_where(where_arr)
59
+ res = select_text(where: where, args: args)
46
60
  parse_verse_list(res)
47
61
  end
48
62
 
63
+ # Get the schema version of the SQLite database of the instance
64
+ def schema_version
65
+ Sqlbible.select_schema_version(@db)
66
+ end
67
+
68
+ # Representation of a verse
49
69
  Verse = Struct.new :osisid, :bookid, :chapter, :verse, :xml, :plaintext, keyword_init: true do
50
70
  def scripref_passage
51
71
  Scripref::Passage.new(b1: bookid, c1: chapter, v1: verse, b2: bookid, c2: chapter, v2: verse)
52
72
  end
53
73
  end
54
74
 
75
+ @bibles_dir = File.join(Dir.home, '.sqlbible/bibles')
76
+
55
77
  class << self
56
78
 
79
+ attr_reader :bibles_dir
80
+
81
+ # Get the database schema as string
57
82
  def db_schema
58
83
  File.read(File.join(__dir__, '../schema.sql'))
59
84
  end
60
85
 
61
- end
86
+ # Get an array of the major and minor version of the database schema of the
87
+ # actual version of the lib
88
+ def schema_major_minor
89
+ lib_db = SQLite3::Database.new(':memory:')
90
+ lib_db.execute_batch(Sqlbible.db_schema)
91
+ select_schema_major_minor(lib_db)
92
+ end
62
93
 
63
- private
94
+ # Get the version of the database schema of the actual version of the lib
95
+ def schema_version
96
+ schema_major_minor.join('.')
97
+ end
98
+
99
+ # Get an array of the major and minor version of an Sqlbible database
100
+ def select_schema_major_minor db
101
+ db.execute("select major, minor from schema_version").first
102
+ end
103
+
104
+ # Get the version of an Sqlbible database
105
+ def select_schema_version db
106
+ select_schema_major_minor(db).join('.')
107
+ end
108
+
109
+ def resolve_db_filename db_name
110
+ fn = db_name.to_s
111
+ if File.basename(fn) == fn
112
+ File.join(bibles_dir, format('%s.sqlbible', fn.sub(/\.sqlbible$/, '')))
113
+ else
114
+ fn
115
+ end
116
+ end
64
117
 
65
- def select_schema_version db
66
- db.execute("select major, minor from schema_version").first
67
118
  end
68
119
 
120
+ private
121
+
69
122
  def check_schema_version
70
- lib_db = SQLite3::Database.new(':memory:')
71
- lib_db.execute_batch(Sqlbible.db_schema)
72
- major_lib, minor_lib = select_schema_version(lib_db)
73
- major_bible, minor_bible = select_schema_version(@db)
123
+ major_lib, minor_lib = Sqlbible.schema_major_minor
124
+ major_bible, minor_bible = Sqlbible.select_schema_major_minor(@db)
74
125
  if major_bible < major_lib || major_bible == major_lib && minor_bible < minor_lib
75
126
  fail 'database schema of bible database is too old'
76
127
  end
metadata CHANGED
@@ -1,13 +1,14 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: sqlbible
3
3
  version: !ruby/object:Gem::Version
4
- version: 1.0.1
4
+ version: 1.2.0
5
5
  platform: ruby
6
+ original_platform: ''
6
7
  authors:
7
8
  - Jan Friedrich
8
9
  bindir: bin
9
10
  cert_chain: []
10
- date: 2024-11-01 00:00:00.000000000 Z
11
+ date: 2024-12-13 00:00:00.000000000 Z
11
12
  dependencies:
12
13
  - !ruby/object:Gem::Dependency
13
14
  name: nokogiri
@@ -24,19 +25,19 @@ dependencies:
24
25
  - !ruby/object:Gem::Version
25
26
  version: '1.16'
26
27
  - !ruby/object:Gem::Dependency
27
- name: optimist
28
+ name: optimist_xl
28
29
  requirement: !ruby/object:Gem::Requirement
29
30
  requirements:
30
31
  - - "~>"
31
32
  - !ruby/object:Gem::Version
32
- version: '3.1'
33
+ version: '3.3'
33
34
  type: :runtime
34
35
  prerelease: false
35
36
  version_requirements: !ruby/object:Gem::Requirement
36
37
  requirements:
37
38
  - - "~>"
38
39
  - !ruby/object:Gem::Version
39
- version: '3.1'
40
+ version: '3.3'
40
41
  - !ruby/object:Gem::Dependency
41
42
  name: scripref
42
43
  requirement: !ruby/object:Gem::Requirement
@@ -90,6 +91,7 @@ files:
90
91
  - bin/sqlbible
91
92
  - lib/sqlbible.rb
92
93
  - lib/sqlbible/convert.rb
94
+ - lib/sqlbible/version.rb
93
95
  - schema.sql
94
96
  homepage: https://bitbucket.org/janfri/sqlbible
95
97
  licenses: