narou 2.4.2 → 2.5.1

Sign up to get free protection for your applications and to get access to all the features.

Potentially problematic release.


This version of narou might be problematic. Click here for more details.

Files changed (53) hide show
  1. checksums.yaml +4 -4
  2. data/.gitignore +1 -0
  3. data/ChangeLog.md +56 -0
  4. data/README.md +56 -29
  5. data/lib/command/convert.rb +39 -7
  6. data/lib/command/diff.rb +42 -11
  7. data/lib/command/inspect.rb +1 -1
  8. data/lib/command/setting.rb +150 -45
  9. data/lib/command/tag.rb +8 -8
  10. data/lib/command/update.rb +57 -1
  11. data/lib/commandbase.rb +3 -0
  12. data/lib/converterbase.rb +17 -9
  13. data/lib/database.rb +4 -0
  14. data/lib/device/epub.rb +1 -1
  15. data/lib/device/ibooks.rb +1 -1
  16. data/lib/device/ibunko.rb +13 -6
  17. data/lib/device/kindle.rb +1 -1
  18. data/lib/device/kobo.rb +1 -1
  19. data/lib/device/reader.rb +1 -1
  20. data/lib/downloader.rb +10 -5
  21. data/lib/helper.rb +114 -3
  22. data/lib/ini.rb +3 -1
  23. data/lib/inventory.rb +3 -1
  24. data/lib/loadconverter.rb +1 -11
  25. data/lib/mailer.rb +1 -0
  26. data/lib/narou.rb +56 -5
  27. data/lib/novelconverter.rb +7 -5
  28. data/lib/novelsetting.rb +116 -63
  29. data/lib/template.rb +4 -4
  30. data/lib/version.rb +1 -1
  31. data/lib/web/appserver.rb +40 -9
  32. data/lib/web/public/resources/narou.library.js +35 -3
  33. data/lib/web/public/resources/narou.ui.js +16 -1
  34. data/lib/web/pushserver.rb +1 -0
  35. data/lib/web/settingmessages.rb +6 -3
  36. data/lib/web/views/diff_list.haml +11 -0
  37. data/lib/web/views/edit_replace_txt.haml +59 -0
  38. data/lib/web/views/help.haml +2 -2
  39. data/lib/web/views/index.haml +6 -4
  40. data/lib/web/views/layout.haml +11 -2
  41. data/lib/web/views/novels/setting.haml +51 -66
  42. data/lib/web/views/settings.haml +52 -15
  43. data/lib/web/views/style.scss +44 -2
  44. data/lib/web/views/widget.haml +6 -8
  45. data/narou.gemspec +45 -6
  46. data/spec/convert_spec.rb +1 -1
  47. data/spec/converterbase_spec.rb +25 -1
  48. data/spec/generator/convert_spec_gen.rb +1 -1
  49. data/spec/helper_spec.rb +8 -0
  50. data/spec/novelsetting_spec.rb +1 -1
  51. data/template/novel.txt.erb +1 -1
  52. data/template/setting.ini.erb +15 -3
  53. metadata +49 -8
@@ -1,6 +1,6 @@
1
1
  -# このページ内専用のjavascriptでjQueryオブジェクトを参照したい場合この関数に記述
2
2
  :javascript
3
- var local_initialize_function = function($) {
3
+ local_initialize_functions.push(function($) {
4
4
  var notification = new Narou.Notification();
5
5
  var stream_console = new Narou.Console(notification, {
6
6
  restore: false, buttons: false
@@ -27,27 +27,14 @@
27
27
  animation: false,
28
28
  container: "body",
29
29
  };
30
+ $("[data-toggle=tooltip]").tooltip(tooltip_opt);
30
31
 
31
- // replace.txt 設定パネル
32
- $(".btn-replace-remove").on("click", function(e) {
33
- e.preventDefault();
34
- if ($(".replace-pattern-tr").size() === 1) {
35
- // 入力欄のtrが全部なくなると追加出来なくなるので、消す前に1個追加しておく
36
- $("#btn-replace-add").trigger("click");
37
- }
38
- $(this).tooltip("destroy").closest("tr").remove();
39
- });
40
- $blank_tr = $(".replace-pattern-tr:last").clone(true); // 読み込み直後の末尾は空なので流用
41
- $("#btn-replace-add").on("click", function(e) {
42
- e.preventDefault();
43
- var $clone = $blank_tr.clone(true);
44
- $clone.find("button").tooltip(tooltip_opt);
45
- $(".replace-pattern-tr:last").after($clone);
46
- $(this).tooltip("hide");
32
+ // セレクトボタン設定
33
+ $(".selectpicker").selectpicker({
34
+ container: "body",
35
+ width: "100%"
47
36
  });
48
-
49
- $("[data-toggle=tooltip]").tooltip(tooltip_opt); // tooltip要素がコピーされないようにclone後に
50
- };
37
+ });
51
38
 
52
39
  %form(action="/novels/#{@id}/setting" method="POST")
53
40
  .navbar.navbar-default.navbar-fixed-top(role="navigation")
@@ -88,12 +75,12 @@
88
75
  ・環境設定で force.* 系設定が有効になっている場合、ここでの該当項目は無視されます<br>
89
76
  ・保存するとこの小説の setting.ini に書かれているコメントは削除されます
90
77
  .list-group
91
- - @default_settings.each do |info|
92
- - name = info[:name]
78
+ - @original_settings.each do |original|
79
+ - name = original[:name]
93
80
  - value = @novel_setting[name]
94
- - help = info[:help].strip.gsub("\n", "<br>")
81
+ - help = original[:help].strip.gsub("\n", "<br>")
95
82
  - list_group_item_style = {}
96
- - force_value = @force_settings["force.#{name}"]
83
+ - force_value = @force_settings[name]
97
84
  - if @error_list[name]
98
85
  - list_group_item_style = {class: "has-error", style: "background-color:#f2dede"}
99
86
  - elsif force_value.nil?.!
@@ -101,20 +88,44 @@
101
88
  .list-group-item.form-group{list_group_item_style}
102
89
  %h4.list-group-item-heading #{name}
103
90
  .list-group-item-text
104
- - case info[:type]
91
+ - case original[:type]
105
92
  - when :boolean
106
- %label(class="switch-light well")
107
- <input type="checkbox" name="#{name}" #{value ? "checked" : ""}>
108
- %span
109
- %span しない
110
- %span する
111
- %a(class="btn btn-primary")
93
+ .switch-toggle.well.switch-3
94
+ <input id="#{name}-nil" type="radio" name="#{name}" value="nil" #{value.nil? ? "checked" : ""}>
95
+ %label(for="#{name}-nil")
96
+ 未設定
97
+ <input id="#{name}-false" type="radio" name="#{name}" value="off" #{value == false ? "checked" : ""}>
98
+ %label(for="#{name}-false")
99
+ しない
100
+ <input id="#{name}-true" type="radio" name="#{name}" value="on" #{value ? "checked" : ""}>
101
+ %label(for="#{name}-true")
102
+ する
103
+ %a.btn.btn-primary
104
+ - when :select
105
+ %div.input-style
106
+ %select{name: name, class: "selectpicker show-tick"}
107
+ %option(value="") 未設定
108
+ - original[:select_keys].each_with_index do |key, index|
109
+ %option{selected: value == key, value: key}
110
+ = original[:select_summaries][index]
111
+ - when :multiple
112
+ %div.input-style
113
+ %select{name: "#{name}[]", class: "selectpicker", multiple: true, title: "未設定"}
114
+ - selected_items = value.to_s.split(",")
115
+ - original[:select_keys].each_with_index do |key, index|
116
+ %option{selected: selected_items.include?(key), value: key}
117
+ = original[:select_summaries][index]
112
118
  - else
113
119
  %input{type:"text", name:name, value:value, class:"form-control",
114
- placeholder:Helper.variable_type_to_description(info[:type]).strip }
120
+ placeholder:Helper.variable_type_to_description(original[:type]).strip }
115
121
  %p #{help}
116
122
  .help-extra-messages
117
- %p デフォルト:#{h value_to_msg(info[:value])}
123
+ %p
124
+ 未設定時:
125
+ - if @default_settings.include?(name)
126
+ = h value_to_msg(@default_settings[name])
127
+ - else
128
+ = h value_to_msg(original[:value])
118
129
  - unless force_value.nil?
119
130
  %p
120
131
  %b force.#{name} が有効になっています(設定値:#{h value_to_msg(force_value)})
@@ -126,39 +137,13 @@
126
137
  %p.panel-settings-link
127
138
  goto <a href="#setting-panel" data-move-to="#setting-panel">変換設定</a>
128
139
 
129
- #replace-panel.panel.panel-info.panel-settings
130
- .panel-heading <b>#{h @novel_title}</b> の置換設定
131
- .panel-body
132
- ・小説の文章を置換する設定を行うことが出来ます(replace.txt を書き換えます)<br>
133
- ・変更を反映させるには再度変換を実行する必要があります<br>
134
- ・保存するとこの小説の replace.txt に書かれているコメントは削除されます<br>
135
- .list-group
136
- .list-group-item.form-group
137
- .list-group-item-text
138
- %table#replace-txt-table
139
- %thead
140
- %tr
141
- %td 対象文字列
142
- %td &nbsp;
143
- %td 置き換える文字列
144
- %td &nbsp;
145
- %tbody
146
- -# 末尾に新規入力用の空要素を追加
147
- - (@replace_pattern + [["",""]]).each do |pattern|
148
- %tr.replace-pattern-tr
149
- %td
150
- %input{type:"text", name:"replace_pattern[][left]", value:pattern[0], class:"form-control"}
151
- %td
152
- %span.glyphicon.glyphicon-chevron-right
153
- %td
154
- %input{type:"text", name:"replace_pattern[][right]", value:pattern[1], class:"form-control"}
155
- %td
156
- %button.btn-replace-remove.btn.btn-default(data-toggle="tooltip" title="削除" data-placement="right")
157
- %span.glyphicon.glyphicon-remove
158
- %tr
159
- %td(colspan=4)
160
- %button#btn-replace-add.btn.btn-default(data-toggle="tooltip" title="1行追加" data-placement="right")
161
- %span.glyphicon.glyphicon-plus
140
+ - @replace_panel_var = { title: "<b>#{h @novel_title}</b> の置換設定",
141
+ panel_class: "panel-info",
142
+ body_class: "",
143
+ body: ["・この小説の文章を置換する設定を行うことが出来ます(replace.txt を書き換えます)",
144
+ "・変更を反映させるには再度変換を実行する必要があります",
145
+ "・保存するとこの小説の replace.txt に書かれているコメントは削除されます"] }
146
+ = haml :edit_replace_txt
162
147
 
163
148
  %input(type="submit" value="設定を保存" class="btn btn-info" style="float:none")
164
149
 
@@ -1,11 +1,16 @@
1
1
  -# このページ内専用のjavascriptでjQueryオブジェクトを参照したい場合この関数に記述
2
2
  :javascript
3
- var local_initialize_function = function($) {
3
+ local_initialize_functions.push(function($) {
4
4
  $("[data-toggle=tooltip]").tooltip({
5
5
  animation: false,
6
6
  container: "body",
7
7
  });
8
- };
8
+ // セレクトボタン設定
9
+ $(".selectpicker").selectpicker({
10
+ container: "body",
11
+ width: "100%"
12
+ });
13
+ });
9
14
 
10
15
  %form(action="/settings" method="POST")
11
16
  %input(type="hidden" name="view_invisible" value="#{@view_invisible ? 1 : 0}")
@@ -35,12 +40,20 @@
35
40
  .container.container-main.theme-showcase(role="main")
36
41
  - @setting_variables.each do |scope, variables|
37
42
  - inventory = Inventory.load("#{scope}_setting", scope)
43
+ - unless @view_invisible
44
+ -# 隠しパラメータは配列の最初の方に集めておく
45
+ -# (リストの最後に隠しパラメータがあると、リストの最下部の表示が切れるため)
46
+ - variables = variables.select { |_, v| v[:invisible] }.merge(variables.reject { |_, v| v[:invisible] })
38
47
 
39
48
  %p.panel-settings-link
40
49
  - if scope == :local
41
50
  goto <a href="#global" data-move-to="#global">Global Variables</a>
51
+
52
+ <a href="#replace-panel" data-move-to="#replace-panel">置換設定</a>
42
53
  - else
43
54
  goto <a href="#local" data-move-to="#local">Local Variables</a>
55
+
56
+ <a href="#replace-panel" data-move-to="#replace-panel">置換設定</a>
44
57
 
45
58
  .panel.panel-primary.panel-settings
46
59
  .panel-heading{id: scope} #{scope.capitalize} Variables
@@ -48,34 +61,35 @@
48
61
  ・各コマンドの設定の変更が出来ます<br>
49
62
  - if scope == :local
50
63
  - if @view_invisible
51
- force.* 系の設定は setting.ini の設定を無視して反映されるようになります<br>
64
+ default.* 系の設定は個別の変換設定で未設定の項目の挙動を指定することが出来ます<br>
65
+ ・force.* 系の設定は個別設定、default.* 等の設定を無視して反映されるようになります<br>
52
66
  ・default_args.* 系の設定は、各種コマンドのオプションを省略した場合に使用されるオプションを指定出来ます<br>
53
67
  - else
54
68
  ・Global な設定はユーザープロファイルに保存され、すべての narou コマンドで使われます<br>
55
69
  - if @view_invisible
56
- ・隠しオプションを非表示にするには<a href="?"><u>ここをクリック</u></a><br>
70
+ ・隠しオプションを非表示にするには<a href="?##{scope}"><u>ここをクリック</u></a><br>
57
71
  - else
58
- ・隠しオプションを表示するには<a href="?view_invisible=1"><u>ここをクリック</u></a><br>
72
+ ・隠しオプションを表示するには<a href="?view_invisible=1##{scope}"><u>ここをクリック</u></a><br>
59
73
  .list-group
60
74
  - variables.each do |name, value|
61
75
  - item = inventory[name]
62
76
  - unless @view_invisible
63
- - if value[2]
64
- - if value[0] == :boolean
77
+ - if value[:invisible]
78
+ - if value[:type] == :boolean
65
79
  - hidden_value = convert_boolean_to_on_off(item)
66
80
  - else
67
81
  - hidden_value = item
68
82
  %input{type:"hidden", name:name, value:hidden_value}
69
83
  - next
70
- - message = Narou::SETTING_VARIABLES_WEBUI_MESSAGES[name] || value[1]
84
+ - message = Narou::SETTING_VARIABLES_WEBUI_MESSAGES[name] || value[:help]
71
85
  - message = message.strip.gsub("\n", "<br>")
72
86
  - error_style = {class: "has-error", style: "background-color:#f2dede"}
73
87
  .list-group-item.form-group{@error_list[name] ? error_style : {}}
74
88
  %h4.list-group-item-heading #{name}
75
89
  .list-group-item-text
76
- - case value[0]
90
+ - case value[:type]
77
91
  - when :boolean
78
- - if name.start_with?("force.")
92
+ - if name =~ /^(force|default)\./
79
93
  .switch-toggle.well.switch-3
80
94
  <input id="#{name}-nil" type="radio" name="#{name}" value="nil" #{item.nil? ? "checked" : ""}>
81
95
  %label(for="#{name}-nil")
@@ -99,17 +113,40 @@
99
113
  %span しない
100
114
  %span する
101
115
  %a.btn.btn-primary
116
+ - when :select
117
+ %div.input-style
118
+ %select{name: name, class: "selectpicker show-tick"}
119
+ %option(value="") 未設定
120
+ - value[:select_keys].each_with_index do |key, index|
121
+ %option{selected: item == key, value: key}
122
+ = value[:select_summaries][index]
123
+ - when :multiple
124
+ %div.input-style
125
+ %select{name: "#{name}[]", class: "selectpicker", multiple: true, title: "未設定"}
126
+ - selected_items = item.to_s.split(",")
127
+ - value[:select_keys].each_with_index do |key, index|
128
+ %option{selected: selected_items.include?(key), value: key}
129
+ = value[:select_summaries][index]
102
130
  - else
103
131
  %input{type:"text", name:name, value:item, class:"form-control",
104
- placeholder:Helper.variable_type_to_description(value[0]).strip }
132
+ placeholder:Helper.variable_type_to_description(value[:type]).strip }
105
133
  %p
106
134
  = message != "" ? message : "&nbsp;"
107
135
  - if @error_list[name]
108
136
  %p.alert-danger
109
137
  = @error_list[name]
110
138
  .clear
111
- .panel-footer
112
- %input.btn.btn-info(type="submit" value="設定を保存" style="float:none")
113
- %span(style="color:gray")
114
- (Local、Globalどちらも保存されます)
115
139
 
140
+ %p.panel-settings-link
141
+ goto <a href="#local" data-move-to="#local">Local Variables</a>
142
+
143
+ <a href="#global" data-move-to="#global">Global Variables</a>
144
+
145
+ - @replace_panel_var = { title: "全小説対象の置換設定",
146
+ panel_class: "panel-primary",
147
+ body_class: "list-group-item-info",
148
+ body: ["・全ての小説に対する置換設定を行うことが出来ます",
149
+ "・変更を反映させるには再度変換を実行する必要があります"] }
150
+ = haml :edit_replace_txt
151
+
152
+ %input(type="submit" value="設定を保存" class="btn btn-info" style="float:none")
@@ -486,6 +486,9 @@ input::-ms-clear {
486
486
  .modal-content {
487
487
  margin-top: 160px;
488
488
  }
489
+ .diff-list-modal .modal-content {
490
+ margin-top: inherit;
491
+ }
489
492
  }
490
493
  @media (max-width:767px) {
491
494
  .modal-content {
@@ -664,13 +667,12 @@ $console-color: white;
664
667
  width: 750px;
665
668
  }
666
669
 
667
- input {
670
+ input, .input-style {
668
671
  @media (min-width: 501px) {
669
672
  float: right;
670
673
  width: 150px;
671
674
  }
672
675
  @media (max-width: 500px) {
673
- float: left;
674
676
  }
675
677
  }
676
678
 
@@ -824,3 +826,43 @@ $console-color: white;
824
826
  display: none;
825
827
  }
826
828
 
829
+ /* 差分表示用ダイアログ */
830
+ .diff-list-container {
831
+ .title {
832
+ size: 2em;
833
+ font-weight: bold;
834
+ padding-bottom: 5px;
835
+ }
836
+ .list {
837
+ .item {
838
+ font-size: 90%;
839
+ cursor: pointer;
840
+ border-top: 1px solid #ddd;
841
+ padding-top: 3px;
842
+ padding-bottom: 3px;
843
+
844
+ ul {
845
+ margin-bottom: 0;
846
+ }
847
+
848
+ &:hover {
849
+ background-color: #eef;
850
+ color: mix(blue, black);
851
+ }
852
+
853
+ .date {
854
+ padding-left: 1em;
855
+ font-weight: bold;
856
+ }
857
+ }
858
+ }
859
+ }
860
+
861
+ /* テーブルのリロードボタン */
862
+ #icon-refresh-table {
863
+ color: #aaa;
864
+ &:hover {
865
+ cursor: pointer;
866
+ color: #777;
867
+ }
868
+ }
@@ -15,13 +15,6 @@
15
15
  <script src="https://oss.maxcdn.com/html5shiv/3.7.2/html5shiv.min.js"></script>
16
16
  <script src="https://oss.maxcdn.com/respond/1.4.2/respond.min.js"></script>
17
17
  %body
18
- :javascript
19
- var local_initialize_function = function($) {
20
- var notification = new Narou.Notification();
21
- var stream_console = new Narou.Console(notification, {
22
- restore: false, buttons: false
23
- });
24
- };
25
18
  :css
26
19
  html, body, .console.fullscreen {
27
20
  height: 100%;
@@ -35,5 +28,10 @@
35
28
  %script{:src => "/resources/perfect-scrollbar.min.js"}
36
29
  %script{:src => "/resources/narou.library.js"}
37
30
  :javascript
38
- if (typeof local_initialize_function !== "undefined") local_initialize_function($);
31
+ $(document).ready(function($) {
32
+ var notification = new Narou.Notification();
33
+ var stream_console = new Narou.Console(notification, {
34
+ restore: false, buttons: false
35
+ });
36
+ });
39
37
 
@@ -32,14 +32,53 @@ Gem::Specification.new do |gem|
32
32
  install_message = <<-EOS
33
33
  #{"*" * 79}
34
34
 
35
- 2.4.2 : 2015/06/07
35
+ 2.5.0 : 2015/07/10
36
36
  ------------------
37
+ #### 追加機能
38
+ - WEB UI の個別メニューから「差分を表示」を選択した際に、過去の差分を選択出来る
39
+ ようにしました
40
+ - WEB UI の個別メニューに「タグを編集」を追加しました
41
+ - 変換設定の各項目の共通設定を変更できる default.* 系設定を追加しました
42
+ + この共通設定は setting.ini で未設定の項目がある場合に適用されます。また、
43
+ force.* が設定されていた場合は setting.ini、共通設定ともに無視されます
44
+ + 例えば `enable_illust` の共通設定を変更したい場合、
45
+ `narou s default.enable_illust=false` とすることで変更出来ます
46
+ (WEB UIからは環境設定のページで隠しオプションを表示)
47
+ - `convert` コマンドに `--ignore-default` オプションを追加しました。変換時の
48
+ default.* 系設定を無視します
49
+ - `convert.copy-to-grouping` オプションを追加しました
50
+ + copy-to で指定したフォルダの中に更に device もしくは convert.multi-device
51
+ で指定した端末毎に振り分けるように出来ます
52
+ + 有効にするには `narou s convert.copy-to-grouping=true` を実行して下さい
53
+ - 全小説を対象にした replace.txt による置換に対応しました
54
+ + narou init を使用したフォルダに replace.txt を設置すると認識します。
55
+ WEB UI においては環境設定にて設定できます
56
+ - `update` コマンドにアップデートの順番を変更する `--sort-by` オプションが追加
57
+ されました(短縮 `-s`)
58
+ + `narou u --sort-by general_update` のように直接コマンドのオプションとして
59
+ 指定するか、 `narou s update.sort-by=general_update` と設定として保存して
60
+ 下さい
61
+ + 指定出来るのは id, last_update(更新日), title(タイトル), author(作者名),
62
+ new_arrivals_date(新着日), general_lastup(最新話掲載日) です
63
+ - WEB UI の設定画面において一部項目をセレクトボックスで選択出来るようにしました
64
+
65
+ #### 仕様変更
66
+ - default.* 系設定追加に伴い、新規DL時の setting.ini の全ての項目がコメント
67
+ アウトされた状態で生成されます。また、WEB UI の個別変換設定画面にて、各項目に
68
+ 「未設定」が追加されます
69
+ - `setting` コマンド(WEB UIにおける環境設定)の項目の順序・表示を変更しました
70
+ - `setting` コマンドの一部項目で適切な値が入力されなかった場合にエラーが出る
71
+ ようになりました
72
+ - WEB UI の個別メニュー内項目の並び順を変更しました
73
+ - WEB UI サーバ起動中にコマンドラインで更新した場合でもサーバを再起動せずに変更
74
+ が反映されるようになりました
75
+
37
76
  #### Bug Fix
38
- - WEB UI のタグ検索結果がページリロードで解除されてしまう不具合を修正
39
- - WEB UI で最新話掲載日を更新したあとにリストを更新するように修正
40
- - 小説家になろうのルビ仕様に追随してない場合があったのを修正
41
- - ハーメルン、ムーンライトノベルズの小説をNコードでDL出来ない不具合を修正
42
- - v2.4.0以前にDLした短編が更新できなくなっていた不具合を修正
77
+ - `enable_insert_word_separator` を有効時に `[` が正常に禁則処理されない問題を
78
+ 修正
79
+ - i文庫形式に変換する際に `enable_illust` の設定が無視されていたのを修正
80
+ - WEB UI サーバ起動中に converter.rb を編集しても反映されなかったのを修正
81
+ - 文章中のリンクが正しく飛べない場合があったのを修正
43
82
 
44
83
  #{"*" * 79}
45
84
  EOS
@@ -40,7 +40,7 @@ describe "convert" do
40
40
  dir = File.dirname(path)
41
41
  filename = File.basename(path)
42
42
  $stdout.silence do
43
- CommandLine.run(["convert", path, "--no-epub", "--no-open", "--ignore-force"])
43
+ CommandLine.run(["convert", path, "--no-epub", "--no-open", "--ignore-force", "--ignore-default"])
44
44
  end
45
45
  output_file = File.join(dir, "[#{AUTHOR}] #{filename}")
46
46
  correct_file = File.join(dir, "correct_#{filename}")