spreadsheet_architect 4.1.0 → 5.0.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 +4 -4
- data/CHANGELOG.md +70 -16
- data/README.md +22 -25
- data/lib/spreadsheet_architect/class_methods/ods.rb +18 -8
- data/lib/spreadsheet_architect/class_methods/xlsx.rb +76 -32
- data/lib/spreadsheet_architect/exceptions.rb +30 -13
- data/lib/spreadsheet_architect/utils/ods.rb +66 -0
- data/lib/spreadsheet_architect/utils/xlsx.rb +61 -32
- data/lib/spreadsheet_architect/utils.rb +29 -51
- data/lib/spreadsheet_architect/version.rb +1 -1
- data/lib/spreadsheet_architect.rb +3 -2
- data/test/dummy_app/app/controllers/spreadsheets_controller.rb +6 -3
- data/test/dummy_app/config/application.rb +4 -12
- data/test/dummy_app/config/environments/test.rb +1 -1
- data/test/dummy_app/config/routes.rb +1 -1
- data/test/dummy_app/db/migrate/20170103234524_add_posts.rb +1 -1
- data/test/dummy_app/db/test.sqlite3 +0 -0
- data/test/dummy_app/log/test.log +82177 -58559
- data/test/dummy_app/tmp/2.0.1/integration/alt_xlsx.xlsx +0 -0
- data/test/dummy_app/tmp/2.0.1/integration/csv.csv +6 -0
- data/test/dummy_app/tmp/2.0.1/integration/ods.ods +0 -0
- data/test/dummy_app/tmp/2.0.1/integration/xlsx.xlsx +0 -0
- data/test/dummy_app/tmp/2.0.1/kitchen_sink.ods +0 -0
- data/test/dummy_app/tmp/2.0.1/kitchen_sink.xlsx +0 -0
- data/test/dummy_app/tmp/2.0.1/models/ActiveModelObject/data.csv +3 -0
- data/test/dummy_app/tmp/2.0.1/models/ActiveModelObject/data.ods +0 -0
- data/test/dummy_app/tmp/2.0.1/models/ActiveModelObject/data.xlsx +0 -0
- data/test/dummy_app/tmp/2.0.1/models/ActiveModelObject/empty.csv +1 -0
- data/test/dummy_app/tmp/2.0.1/models/ActiveModelObject/empty.ods +0 -0
- data/test/dummy_app/tmp/2.0.1/models/ActiveModelObject/empty.xlsx +0 -0
- data/test/dummy_app/tmp/2.0.1/models/ActiveModelObject/instances.csv +6 -0
- data/test/dummy_app/tmp/2.0.1/models/ActiveModelObject/instances.ods +0 -0
- data/test/dummy_app/tmp/2.0.1/models/ActiveModelObject/instances.xlsx +0 -0
- data/test/dummy_app/tmp/2.0.1/models/CustomColumnsMethodPost/data.csv +3 -0
- data/test/dummy_app/tmp/2.0.1/models/CustomColumnsMethodPost/data.ods +0 -0
- data/test/dummy_app/tmp/2.0.1/models/CustomColumnsMethodPost/data.xlsx +0 -0
- data/test/dummy_app/tmp/2.0.1/models/CustomColumnsMethodPost/empty.csv +0 -0
- data/test/dummy_app/tmp/2.0.1/models/CustomColumnsMethodPost/empty.ods +0 -0
- data/test/dummy_app/tmp/2.0.1/models/CustomColumnsMethodPost/empty.xlsx +0 -0
- data/test/dummy_app/tmp/2.0.1/models/CustomColumnsMethodPost/instances.csv +6 -0
- data/test/dummy_app/tmp/2.0.1/models/CustomColumnsMethodPost/instances.ods +0 -0
- data/test/dummy_app/tmp/2.0.1/models/CustomColumnsMethodPost/instances.xlsx +0 -0
- data/test/dummy_app/tmp/2.0.1/models/CustomPost/data.csv +3 -0
- data/test/dummy_app/tmp/2.0.1/models/CustomPost/data.ods +0 -0
- data/test/dummy_app/tmp/2.0.1/models/CustomPost/data.xlsx +0 -0
- data/test/dummy_app/tmp/2.0.1/models/CustomPost/empty.csv +1 -0
- data/test/dummy_app/tmp/2.0.1/models/CustomPost/empty.ods +0 -0
- data/test/dummy_app/tmp/2.0.1/models/CustomPost/empty.xlsx +0 -0
- data/test/dummy_app/tmp/2.0.1/models/CustomPost/instances.csv +6 -0
- data/test/dummy_app/tmp/2.0.1/models/CustomPost/instances.ods +0 -0
- data/test/dummy_app/tmp/2.0.1/models/CustomPost/instances.xlsx +0 -0
- data/test/dummy_app/tmp/2.0.1/models/LegacyPlainRubyObject/data.csv +3 -0
- data/test/dummy_app/tmp/2.0.1/models/LegacyPlainRubyObject/data.ods +0 -0
- data/test/dummy_app/tmp/2.0.1/models/LegacyPlainRubyObject/data.xlsx +0 -0
- data/test/dummy_app/tmp/2.0.1/models/LegacyPlainRubyObject/empty.csv +1 -0
- data/test/dummy_app/tmp/2.0.1/models/LegacyPlainRubyObject/empty.ods +0 -0
- data/test/dummy_app/tmp/2.0.1/models/LegacyPlainRubyObject/empty.xlsx +0 -0
- data/test/dummy_app/tmp/2.0.1/models/LegacyPlainRubyObject/instances.csv +6 -0
- data/test/dummy_app/tmp/2.0.1/models/LegacyPlainRubyObject/instances.ods +0 -0
- data/test/dummy_app/tmp/2.0.1/models/LegacyPlainRubyObject/instances.xlsx +0 -0
- data/test/dummy_app/tmp/2.0.1/models/PlainRubyObject/data.csv +3 -0
- data/test/dummy_app/tmp/2.0.1/models/PlainRubyObject/data.ods +0 -0
- data/test/dummy_app/tmp/2.0.1/models/PlainRubyObject/data.xlsx +0 -0
- data/test/dummy_app/tmp/2.0.1/models/PlainRubyObject/empty.csv +1 -0
- data/test/dummy_app/tmp/2.0.1/models/PlainRubyObject/empty.ods +0 -0
- data/test/dummy_app/tmp/2.0.1/models/PlainRubyObject/empty.xlsx +0 -0
- data/test/dummy_app/tmp/2.0.1/models/PlainRubyObject/instances.csv +6 -0
- data/test/dummy_app/tmp/2.0.1/models/PlainRubyObject/instances.ods +0 -0
- data/test/dummy_app/tmp/2.0.1/models/PlainRubyObject/instances.xlsx +0 -0
- data/test/dummy_app/tmp/2.0.1/models/Post/data.csv +3 -0
- data/test/dummy_app/tmp/2.0.1/models/Post/data.ods +0 -0
- data/test/dummy_app/tmp/2.0.1/models/Post/data.xlsx +0 -0
- data/test/dummy_app/tmp/2.0.1/models/Post/empty.csv +0 -0
- data/test/dummy_app/tmp/2.0.1/models/Post/empty.ods +0 -0
- data/test/dummy_app/tmp/2.0.1/models/Post/empty.xlsx +0 -0
- data/test/dummy_app/tmp/2.0.1/models/Post/instances.csv +6 -0
- data/test/dummy_app/tmp/2.0.1/models/Post/instances.ods +0 -0
- data/test/dummy_app/tmp/2.0.1/models/Post/instances.xlsx +0 -0
- data/test/dummy_app/tmp/2.0.1/multi_sheet.ods +0 -0
- data/test/dummy_app/tmp/2.0.1/multi_sheet.xlsx +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/integration/alt_xlsx.xlsx +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/integration/csv.csv +5 -5
- data/test/dummy_app/tmp/3.0.0.pre/integration/ods.ods +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/integration/xlsx.xlsx +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/kitchen_sink.ods +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/kitchen_sink.xlsx +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/ActiveModelObject/data.csv +1 -1
- data/test/dummy_app/tmp/3.0.0.pre/models/ActiveModelObject/data.ods +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/ActiveModelObject/data.xlsx +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/ActiveModelObject/empty.ods +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/ActiveModelObject/empty.xlsx +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/ActiveModelObject/instances.csv +5 -5
- data/test/dummy_app/tmp/3.0.0.pre/models/ActiveModelObject/instances.ods +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/ActiveModelObject/instances.xlsx +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/CustomColumnsMethodPost/data.csv +1 -1
- data/test/dummy_app/tmp/3.0.0.pre/models/CustomColumnsMethodPost/data.ods +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/CustomColumnsMethodPost/data.xlsx +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/CustomColumnsMethodPost/empty.ods +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/CustomColumnsMethodPost/empty.xlsx +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/CustomColumnsMethodPost/instances.csv +5 -5
- data/test/dummy_app/tmp/3.0.0.pre/models/CustomColumnsMethodPost/instances.ods +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/CustomColumnsMethodPost/instances.xlsx +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/CustomPost/data.csv +1 -1
- data/test/dummy_app/tmp/3.0.0.pre/models/CustomPost/data.ods +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/CustomPost/data.xlsx +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/CustomPost/empty.ods +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/CustomPost/empty.xlsx +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/CustomPost/instances.csv +5 -5
- data/test/dummy_app/tmp/3.0.0.pre/models/CustomPost/instances.ods +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/CustomPost/instances.xlsx +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/LegacyPlainRubyObject/data.csv +1 -1
- data/test/dummy_app/tmp/3.0.0.pre/models/LegacyPlainRubyObject/data.ods +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/LegacyPlainRubyObject/data.xlsx +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/LegacyPlainRubyObject/empty.ods +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/LegacyPlainRubyObject/empty.xlsx +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/LegacyPlainRubyObject/instances.csv +5 -5
- data/test/dummy_app/tmp/3.0.0.pre/models/LegacyPlainRubyObject/instances.ods +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/LegacyPlainRubyObject/instances.xlsx +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/PlainRubyObject/data.csv +1 -1
- data/test/dummy_app/tmp/3.0.0.pre/models/PlainRubyObject/data.ods +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/PlainRubyObject/data.xlsx +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/PlainRubyObject/empty.csv +0 -1
- data/test/dummy_app/tmp/3.0.0.pre/models/PlainRubyObject/empty.ods +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/PlainRubyObject/empty.xlsx +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/PlainRubyObject/instances.csv +5 -5
- data/test/dummy_app/tmp/3.0.0.pre/models/PlainRubyObject/instances.ods +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/PlainRubyObject/instances.xlsx +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/Post/data.csv +1 -1
- data/test/dummy_app/tmp/3.0.0.pre/models/Post/data.ods +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/Post/data.xlsx +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/Post/empty.csv +1 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/Post/empty.ods +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/Post/empty.xlsx +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/Post/instances.csv +5 -5
- data/test/dummy_app/tmp/3.0.0.pre/models/Post/instances.ods +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/models/Post/instances.xlsx +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/multi_sheet.ods +0 -0
- data/test/dummy_app/tmp/3.0.0.pre/multi_sheet.xlsx +0 -0
- data/test/dummy_app/tmp/axlsx-master/integration/alt_xlsx.xlsx +0 -0
- data/test/dummy_app/tmp/axlsx-master/integration/csv.csv +6 -0
- data/test/dummy_app/tmp/axlsx-master/integration/ods.ods +0 -0
- data/test/dummy_app/tmp/axlsx-master/integration/xlsx.xlsx +0 -0
- data/test/dummy_app/tmp/axlsx-master/kitchen_sink.ods +0 -0
- data/test/dummy_app/tmp/axlsx-master/kitchen_sink.xlsx +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/ActiveModelObject/data.csv +4 -0
- data/test/dummy_app/tmp/axlsx-master/models/ActiveModelObject/data.ods +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/ActiveModelObject/data.xlsx +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/ActiveModelObject/empty.csv +1 -0
- data/test/dummy_app/tmp/axlsx-master/models/ActiveModelObject/empty.ods +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/ActiveModelObject/empty.xlsx +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/ActiveModelObject/instances.csv +6 -0
- data/test/dummy_app/tmp/axlsx-master/models/ActiveModelObject/instances.ods +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/ActiveModelObject/instances.xlsx +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/CustomColumnsMethodPost/data.csv +4 -0
- data/test/dummy_app/tmp/axlsx-master/models/CustomColumnsMethodPost/data.ods +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/CustomColumnsMethodPost/data.xlsx +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/CustomColumnsMethodPost/empty.csv +1 -0
- data/test/dummy_app/tmp/axlsx-master/models/CustomColumnsMethodPost/empty.ods +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/CustomColumnsMethodPost/empty.xlsx +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/CustomColumnsMethodPost/instances.csv +6 -0
- data/test/dummy_app/tmp/axlsx-master/models/CustomColumnsMethodPost/instances.ods +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/CustomColumnsMethodPost/instances.xlsx +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/CustomPost/data.csv +4 -0
- data/test/dummy_app/tmp/axlsx-master/models/CustomPost/data.ods +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/CustomPost/data.xlsx +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/CustomPost/empty.csv +1 -0
- data/test/dummy_app/tmp/axlsx-master/models/CustomPost/empty.ods +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/CustomPost/empty.xlsx +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/CustomPost/instances.csv +6 -0
- data/test/dummy_app/tmp/axlsx-master/models/CustomPost/instances.ods +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/CustomPost/instances.xlsx +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/LegacyPlainRubyObject/data.csv +4 -0
- data/test/dummy_app/tmp/axlsx-master/models/LegacyPlainRubyObject/data.ods +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/LegacyPlainRubyObject/data.xlsx +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/LegacyPlainRubyObject/empty.csv +1 -0
- data/test/dummy_app/tmp/axlsx-master/models/LegacyPlainRubyObject/empty.ods +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/LegacyPlainRubyObject/empty.xlsx +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/LegacyPlainRubyObject/instances.csv +6 -0
- data/test/dummy_app/tmp/axlsx-master/models/LegacyPlainRubyObject/instances.ods +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/LegacyPlainRubyObject/instances.xlsx +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/PlainRubyObject/data.csv +4 -0
- data/test/dummy_app/tmp/axlsx-master/models/PlainRubyObject/data.ods +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/PlainRubyObject/data.xlsx +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/PlainRubyObject/empty.csv +1 -0
- data/test/dummy_app/tmp/axlsx-master/models/PlainRubyObject/empty.ods +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/PlainRubyObject/empty.xlsx +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/PlainRubyObject/instances.csv +6 -0
- data/test/dummy_app/tmp/axlsx-master/models/PlainRubyObject/instances.ods +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/PlainRubyObject/instances.xlsx +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/Post/data.csv +4 -0
- data/test/dummy_app/tmp/axlsx-master/models/Post/data.ods +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/Post/data.xlsx +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/Post/empty.csv +1 -0
- data/test/dummy_app/tmp/axlsx-master/models/Post/empty.ods +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/Post/empty.xlsx +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/Post/instances.csv +6 -0
- data/test/dummy_app/tmp/axlsx-master/models/Post/instances.ods +0 -0
- data/test/dummy_app/tmp/axlsx-master/models/Post/instances.xlsx +0 -0
- data/test/dummy_app/tmp/axlsx-master/multi_sheet.ods +0 -0
- data/test/dummy_app/tmp/axlsx-master/multi_sheet.xlsx +0 -0
- data/test/integration/application_test.rb +8 -16
- data/test/models/all_models_test.rb +15 -19
- data/test/test_helper.rb +48 -9
- data/test/unit/ods/general_test.rb +121 -0
- data/test/unit/{formats_test.rb → rails/formats_test.rb} +1 -1
- data/test/unit/{exceptions_test.rb → spreadsheet_architect/exceptions_test.rb} +19 -15
- data/test/unit/{general_test.rb → spreadsheet_architect/spreadsheet_architect_test.rb} +3 -3
- data/test/unit/spreadsheet_architect/utils/ods_test.rb +58 -0
- data/test/unit/{xlsx_utils_test.rb → spreadsheet_architect/utils/xlsx_test.rb} +13 -21
- data/test/unit/{utils_test.rb → spreadsheet_architect/utils_test.rb} +15 -31
- data/test/unit/xlsx/freeze_test.rb +79 -0
- data/test/unit/xlsx/general_test.rb +199 -0
- metadata +395 -128
- data/test/dummy_app/config/environments/development.rb +0 -30
- data/test/dummy_app/config/environments/production.rb +0 -60
- data/test/unit/kitchen_sink_test.rb +0 -110
- data/test/unit/multi_sheet_test.rb +0 -29
- data/test/unit/regressions_test.rb +0 -11
- data/test/unit/xlsx_freeze_test.rb +0 -44
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: c88ecaffa3abed6ef127dc13d42c612ebf224c6d8552590d68ae544af2713f93
|
|
4
|
+
data.tar.gz: d0e864c2f50e99040f932da595b7270dd0e9c0161fc1189e6d99cb43126f6b5a
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: dfc0caea596d57bd5aa88cd3b5ff3cebfca8b1299d1660e9995ca93837746d21420a90e0f427df9b3f8e73c13914a24b137572c005ee16fafdeeb6ddaf18b95d
|
|
7
|
+
data.tar.gz: c31f408e271453d46454e4f85ad2437a2539e39973186a8889c917a338f9e5f57f9ef3f3f28797955d61f8daa6a7100ffb46624ab3974c4bfd9273cc5cacba29
|
data/CHANGELOG.md
CHANGED
|
@@ -1,14 +1,34 @@
|
|
|
1
1
|
CHANGELOG
|
|
2
2
|
---------
|
|
3
3
|
|
|
4
|
-
- **Unreleased**
|
|
4
|
+
- **Unreleased** - [View Diff](https://github.com/westonganger/spreadsheet_architect/compare/v5.0.0...master)
|
|
5
5
|
- Nothing yet
|
|
6
|
-
|
|
6
|
+
|
|
7
|
+
- **5.0.0** - [View Diff](https://github.com/westonganger/spreadsheet_architect/compare/v4.2.0...v5.0.0)
|
|
8
|
+
- [#52](https://github.com/westonganger/spreadsheet_architect/pull/52) - Update to caxlsx v3.3.0+ which now contains the axlsx_styler code, so we drop the dependency on axlsx_styler
|
|
9
|
+
- [#38](https://github.com/westonganger/spreadsheet_architect/pull/38) - **Breaking Change** - Add `escape_formulas` option for xlsx spreadsheets. This is a breaking change because we default to `escape_formulas: true` whereas before there was no formula escaping at all. The reasoning for this breaking change is that creating spreadsheets where many of the fields contain direct user input are a large majority compared to use cases that involve formulas.
|
|
10
|
+
- [#39](https://github.com/westonganger/spreadsheet_architect/pull/39) - Add option `use_zero_based_row_index: true` (Default `false`) which allows you to use zero-based row indexes instead of the default 1-based row indexes. Recomended to set this option for the whole project. The original reason it was designed to be 1-based is because spreadsheet row numbers literally start with 1. However this tends to be unituitive for the developer because columns use zero based indexes because they use letter-based notation instead.
|
|
11
|
+
- [#40](https://github.com/westonganger/spreadsheet_architect/pull/40) - Improve argument handling for freeze option and add support for all Axlsx supported options for panes using the `:freeze` hash. See test case for example (./test/unit/xlsx_freeze_test.rb)
|
|
12
|
+
- [#42](https://github.com/westonganger/spreadsheet_architect/pull/42) - Improve exceptions and messages regarding invalid ranges
|
|
13
|
+
- [#45](https://github.com/westonganger/spreadsheet_architect/pull/45) - For `to_xlsx`, dont add empty header row when `header: true`
|
|
14
|
+
- [#44](https://github.com/westonganger/spreadsheet_architect/pull/44) - Add support for hyperlinks in XLSX and ODS
|
|
15
|
+
- [#49](https://github.com/westonganger/spreadsheet_architect/pulls/49) - Extracted some ODS methods from `SpreadsheetArchitect::Utils` to `SpreadsheetArchitect::Utils::ODS`
|
|
16
|
+
- [#51](https://github.com/westonganger/spreadsheet_architect/pulls/51) - Add Proc support to `:column_types`
|
|
17
|
+
|
|
18
|
+
- **4.2.0** - May 27, 2021 - [View Diff](https://github.com/westonganger/spreadsheet_architect/compare/v4.1.0...v4.2.0)
|
|
19
|
+
- Add option `:skip_defaults` which removes the defaults and default styles. Particularily useful for heavily customized spreadsheets where the default styles get in the way.
|
|
20
|
+
- Fix bug where styles werent being un-applied when using the `false` value.
|
|
21
|
+
- Add style aliases for `:valign` and `:wrap_text`
|
|
22
|
+
- Fix error with `headers: false`, previously had to use `headers: []`
|
|
23
|
+
|
|
24
|
+
- **4.1.0** - Nov 20, 2020 - [View Diff](https://github.com/westonganger/spreadsheet_architect/compare/v4.0.1...v4.1.0)
|
|
7
25
|
- Raise ArgumentError when invalid option names are given
|
|
8
|
-
|
|
26
|
+
|
|
27
|
+
- **4.0.1** - Nov 20, 2020 - [View Diff](https://github.com/westonganger/spreadsheet_architect/compare/v4.0.0...v4.0.1)
|
|
9
28
|
- Fix bug with `headers: false` where a blank header row is still added
|
|
10
29
|
- Fix Bug for older version of `caxlsx` v2.0.2
|
|
11
|
-
|
|
30
|
+
|
|
31
|
+
- **4.0.0** - Mar 3, 2020 - [View Diff](https://github.com/westonganger/spreadsheet_architect/compare/v3.3.1...v4.0.0)
|
|
12
32
|
- Switch to the `caxlsx` gem (Community Axlsx) from the legacy unmaintained `axlsx` gem. Axlsx has had a long history of being poorly maintained so this community gem improves the situation.
|
|
13
33
|
- Require Ruby 2.3+
|
|
14
34
|
- Ensure all options using Hash are automatically converted to symbol only hashes
|
|
@@ -16,29 +36,35 @@ CHANGELOG
|
|
|
16
36
|
- Add XLSX option `:freeze_headers` to freeze the headers of your spreadsheet
|
|
17
37
|
- Remove old Axlsx patch for column width
|
|
18
38
|
- Backport new code for `string_width` calculations to Axlsx 3.0.1 and below.
|
|
19
|
-
|
|
39
|
+
|
|
40
|
+
- **3.3.1** - Dec 2, 2019 - [View Diff](https://github.com/westonganger/spreadsheet_architect/compare/v3.3.0...v3.3.1)
|
|
20
41
|
- [Issue #30](https://github.com/westonganger/spreadsheet_architect/issues/30) - Fix duplicate constant warning for XLSX_COLUMN_TYPES
|
|
21
|
-
|
|
42
|
+
|
|
43
|
+
- **3.3.0** - Nov 28, 2019 - [View Diff](https://github.com/westonganger/spreadsheet_architect/compare/v3.2.1...v3.3.0)
|
|
22
44
|
- Fix `:borders` option, was broken in v3.2.1
|
|
23
45
|
- Fix bug when passing `false` to `:headers` option
|
|
24
46
|
- Raise error when unsupported column type is passed
|
|
25
47
|
- Remove claimed support for `:currency` and `:percent` for ODS spreadsheets as they were not working. PR Wanted.
|
|
26
|
-
|
|
48
|
+
|
|
49
|
+
- **3.2.1** - April 10, 2019 - [View Diff](https://github.com/westonganger/spreadsheet_architect/compare/v3.2.0...v3.2.1)
|
|
27
50
|
- Fix bug when using `column_style` option with `include_header: true` & letter based column numbering
|
|
28
|
-
|
|
51
|
+
|
|
52
|
+
- **3.2.0** - September 14, 2018 - [View Diff](https://github.com/westonganger/spreadsheet_architect/compare/v3.1.0...v3.2.0)
|
|
29
53
|
- Change implementation of `:column_styles` option to utilize `axlsx_styler` instead of the built-in axlsx `col_style` method. The reason for the switch is that `col_style` would overwrite all previously set styles. `axlsx_styler` already has the ability to add onto existing styles and is what is currently utilized by `range_styles`.
|
|
30
54
|
- Date / Time formatting is now set per cell instead of on the entire column.
|
|
31
55
|
- Default Date formatting for `xlsx` changed from `m/d/yyyy` to `yyyy-mm-dd`
|
|
32
56
|
- Default Time/DateTime formatting for `xlsx` changed from `yyyy/m/d h:mm AM/PM` to `yyyy-mm-dd h:mm AM/PM`
|
|
33
57
|
- Fix bug where the ActionController::Renderer `:filename` option was ignored when an AR::Relation passed directly to the renderer without first calling `to_#{format}`
|
|
34
|
-
|
|
58
|
+
|
|
59
|
+
- **3.1.0** - August 19, 2018 - [View Diff](https://github.com/westonganger/spreadsheet_architect/compare/v3.0.0...v3.1.0)
|
|
35
60
|
- Add new option `:conditional_row_styles` to `to_xlsx`.
|
|
36
61
|
- Add ability to pass an alternative method name as a Symbol/String to the `:spreadsheet_columns` option.
|
|
37
62
|
- Replace all usage of the legacy method `instance_eval` with the proper method `send`.
|
|
38
63
|
- [#23](https://github.com/westonganger/spreadsheet_architect/issues/23#issuecomment-412803761) - Fix bug where custom `columns_widths` in xlsx spreadsheets might not get set correctly.
|
|
39
64
|
- All exceptions now inherit from the appropriate ruby core exception classes
|
|
40
65
|
- `SpreadsheetArchitect::Exceptions::InvalidOptionError` renamed to `SpreadsheetArchitect::Exceptions::OptionTypeError`
|
|
41
|
-
|
|
66
|
+
|
|
67
|
+
- **3.0.0** - July 6, 2018 - [View Diff](https://github.com/westonganger/spreadsheet_architect/compare/v2.1.2...v3.0.0)
|
|
42
68
|
- [#16](https://github.com/westonganger/spreadsheet_architect/issues/16) - Add ability to pass :instances option to SpreadsheetArchitect class methods
|
|
43
69
|
- [#16](https://github.com/westonganger/spreadsheet_architect/issues/16) - Remove Plain Ruby syntax `Post.to_xlsx(instances: posts_array)` in favor of `SpreadsheetArchitect.to_xlsx(instance: posts_array)`. However, it may still work at this time if configured correctly.
|
|
44
70
|
- Fix project-wide and model-level defaults before only `header_style`, `row_style`, & `sheet_name` were being utilized.
|
|
@@ -53,12 +79,15 @@ CHANGELOG
|
|
|
53
79
|
- Remove all Rails generators `spreadsheet_architect:add_default_options`. No need since its just as easy to copy from the README
|
|
54
80
|
- Major overhaul of test suite, add a ton more tests, for DRYness use resursion for tests when appropriate
|
|
55
81
|
- Use appraisal to test various `axlsx` versions
|
|
56
|
-
|
|
82
|
+
|
|
83
|
+
- **2.1.2** - July 6, 2018 - [View Diff](https://github.com/westonganger/spreadsheet_architect/compare/v2.1.1...v2.1.2)
|
|
57
84
|
- Fix bug where everything was underlined by default in Excel (LibreOffice was working correctly). For some reason, `false` in `:u` or `:underline` was incorrectly being treated as `true` but only within Excel. Now anytime `false` is encountered for either `:u` or `:underline` it is now converted to `nil`
|
|
58
85
|
- Fix bug where empty xlsx spreadsheets were corrupt when trying to open with Excel (LibreOffice was working correctly). This only occured when containing no headers and empty `:data` option which resulted in a package with no sheets.
|
|
59
|
-
|
|
86
|
+
|
|
87
|
+
- **2.1.1** - July 4, 2018 - [View Diff](https://github.com/westonganger/spreadsheet_architect/compare/v2.1.0...v2.1.1)
|
|
60
88
|
- [#18](https://github.com/westonganger/spreadsheet_architect/pull/18) - Fix controller bug when using an non-ActiveRecord ORM only within Rails
|
|
61
|
-
|
|
89
|
+
|
|
90
|
+
- **2.1.0** - June 20, 2018 - [View Diff](https://github.com/westonganger/spreadsheet_architect/compare/v2.0.2...v2.1.0)
|
|
62
91
|
- [#15](https://github.com/westonganger/spreadsheet_architect/pull/15) - Improved the method symbolize_keys. This method did not work properly for nested objects.
|
|
63
92
|
- [PR #15](https://github.com/westonganger/spreadsheet_architect/pull/15) - Added the ability to pass `:text_wrap` option within the `:alignment` style
|
|
64
93
|
- Make axlsx styles higher precendence over Spreadsheet Architect style aliases
|
|
@@ -66,14 +95,17 @@ CHANGELOG
|
|
|
66
95
|
- Due to [RODF bug](https://github.com/thiagoarrais/rodf/issues/19) convert all Date and Time cells to String in ODS spreadsheets
|
|
67
96
|
- Improve test suite
|
|
68
97
|
- Dont test against Ruby versions that Rails no longer supports. Gem code should remain compatible with Ruby 1.9.3.
|
|
69
|
-
|
|
98
|
+
|
|
99
|
+
- **2.0.2** - July 14 2017 - [View Diff](https://github.com/westonganger/spreadsheet_architect/compare/v2.0.1...v2.0.2)
|
|
70
100
|
- Fix bug with range styles rows option not counting headers
|
|
71
101
|
- Fix bug with range styles rows :all option
|
|
72
|
-
|
|
102
|
+
|
|
103
|
+
- **2.0.1** - February 16 2017 - [View Diff](https://github.com/westonganger/spreadsheet_architect/compare/v2.0.0...v2.0.1)
|
|
73
104
|
- Fix bug where `SpreadsheetArchitect.default_options` and `SPREADSHEET_OPTIONS` were being overwritten
|
|
74
105
|
- Fix bug where col_styles ignored previous styles on header when using `include_header` option
|
|
75
106
|
- Errors now try to provide which value is the cause
|
|
76
|
-
|
|
107
|
+
|
|
108
|
+
- **2.0.0** - January 28 2017 - [View Diff](https://github.com/westonganger/spreadsheet_architect/compare/v1.4.8...v2.0.0)
|
|
77
109
|
- Add to xlsx: `merges`, `column_styles`, `range_styles`, `borders`, `column_widths` multi-row headers, date/time default format_code
|
|
78
110
|
- Add `column_types` option for xlsx and ods
|
|
79
111
|
- Add ability to make multi-sheet spreadsheets in XLSX & ODS
|
|
@@ -81,52 +113,74 @@ CHANGELOG
|
|
|
81
113
|
- Add Examples
|
|
82
114
|
- Add Axlsx Style Reference
|
|
83
115
|
- Refractor into smaller files
|
|
116
|
+
|
|
84
117
|
- **1.4.8** - December 6 2016
|
|
85
118
|
- Lock `rodf` gem to v0.3.7 for last v1 version of this gem
|
|
119
|
+
|
|
86
120
|
- **1.4.7** - November 7 2016
|
|
87
121
|
- Fix method arguments for `to_rodf_spreadsheet` method
|
|
122
|
+
|
|
88
123
|
- **1.4.6** - May 16 2016
|
|
89
124
|
- Fix hash syntax for support of ruby v2.1 and below
|
|
125
|
+
|
|
90
126
|
- **1.4.5** - May 4 2016
|
|
91
127
|
- Bug fixes
|
|
128
|
+
|
|
92
129
|
- **1.4.4** - May 3 2016
|
|
93
130
|
- Add Ability to add format_code to all numbers body rows
|
|
131
|
+
|
|
94
132
|
- **1.4.3** - May 3 2016
|
|
95
133
|
- Bug fixes
|
|
134
|
+
|
|
96
135
|
- **1.4.2** - May 3 2016
|
|
97
136
|
- Add to_axlsx_package, to_rodf_spreadsheet methods for the item to be further manipulated. Ex. axlsx_styler
|
|
137
|
+
|
|
98
138
|
- **1.4.1** - May 2 2016
|
|
99
139
|
- Add rails generator for project defaults initializer
|
|
140
|
+
|
|
100
141
|
- **1.4.0** - April 29 2016
|
|
101
142
|
- Add to_xlsx, to_ods, & to_csv to SpreadsheetArchitect model for direct calling by passing in cell data
|
|
143
|
+
|
|
102
144
|
- **1.3.0** - April 21 2016
|
|
103
145
|
- Add ability to create class/model and project option defaults
|
|
146
|
+
|
|
104
147
|
- **1.2.5** - March 25 2016
|
|
105
148
|
- Fix each_with_index bug
|
|
149
|
+
|
|
106
150
|
- **1.2.4** - March 24 2016
|
|
107
151
|
- Fix cell type logic for symbol methods
|
|
152
|
+
|
|
108
153
|
- **1.2.3** - March 20 2016
|
|
109
154
|
- Fix cell type logic
|
|
155
|
+
|
|
110
156
|
- **1.2.2** - March 19 2016
|
|
111
157
|
- Make cell type numeric if value is numeric
|
|
158
|
+
|
|
112
159
|
- **1.2.1** - March 13 2016
|
|
113
160
|
- Better error reporting
|
|
114
161
|
- Fix for Plain ruby models
|
|
162
|
+
|
|
115
163
|
- **1.2.0** - March 10 2016
|
|
116
164
|
- Fix Bug: first row data repeated for all records on custom values
|
|
165
|
+
|
|
117
166
|
- **1.1.0** - March 3 2016
|
|
118
167
|
- Breaking Change - Move spreadsheet_columns method from the class to the instance
|
|
119
168
|
- Fix Bug: remove default underline on cells
|
|
169
|
+
|
|
120
170
|
- **1.0.4** - March 1 2016
|
|
121
171
|
- Extract helper methods to seperate module
|
|
122
172
|
- Improve readme
|
|
173
|
+
|
|
123
174
|
- **1.0.3** - March 1 2016
|
|
124
175
|
- Fix/Improve renderers
|
|
125
176
|
- Fix header default background color
|
|
126
177
|
- Fix default columns
|
|
178
|
+
|
|
127
179
|
- **1.0.2** - February 26 2016
|
|
128
180
|
- Enhance Style options
|
|
181
|
+
|
|
129
182
|
- **1.0.1** - February 26 2016
|
|
130
183
|
- Fix bug in renderers
|
|
184
|
+
|
|
131
185
|
- **1.0.0** - February 26 2016
|
|
132
186
|
- Gem Initial Release
|
data/README.md
CHANGED
|
@@ -1,9 +1,8 @@
|
|
|
1
1
|
# Spreadsheet Architect
|
|
2
2
|
|
|
3
3
|
<a href="https://badge.fury.io/rb/spreadsheet_architect" target="_blank"><img height="21" style='border:0px;height:21px;' border='0' src="https://badge.fury.io/rb/spreadsheet_architect.svg" alt="Gem Version"></a>
|
|
4
|
-
<a href='https://
|
|
4
|
+
<a href='https://github.com/westonganger/spreadsheet_architect/actions' target='_blank'><img src="https://github.com/westonganger/spreadsheet_architect/workflows/Tests/badge.svg" style="max-width:100%;" height='21' style='border:0px;height:21px;' border='0' alt="CI Status"></a>
|
|
5
5
|
<a href='https://rubygems.org/gems/spreadsheet_architect' target='_blank'><img height='21' style='border:0px;height:21px;' src='https://ruby-gem-downloads-badge.herokuapp.com/spreadsheet_architect?label=rubygems&type=total&total_label=downloads&color=brightgreen' border='0' alt='RubyGems Downloads' /></a>
|
|
6
|
-
<a href='https://ko-fi.com/A5071NK' target='_blank'><img height='22' style='border:0px;height:22px;' src='https://az743702.vo.msecnd.net/cdn/kofi1.png?v=a' border='0' alt='Buy Me a Coffee' /></a>
|
|
7
6
|
|
|
8
7
|
Spreadsheet Architect is a library that allows you to create XLSX, ODS, or CSV spreadsheets super easily from ActiveRecord relations, plain Ruby objects, or tabular data.
|
|
9
8
|
|
|
@@ -92,7 +91,7 @@ If you want to use a different method name then `spreadsheet_columns` you can pa
|
|
|
92
91
|
Post.to_xlsx(instances: posts, spreadsheet_columns: :my_special_method)
|
|
93
92
|
```
|
|
94
93
|
|
|
95
|
-
Alternatively, you can pass a Proc
|
|
94
|
+
Alternatively, you can pass a Proc to the `spreadsheet_columns` option. For those purists that really dont want to define any extra `spreadsheet_columns` instance method on your model, this option can help you work with that methodology.
|
|
96
95
|
|
|
97
96
|
```ruby
|
|
98
97
|
Post.to_xlsx(instances: posts, spreadsheet_columns: Proc.new{|instance|
|
|
@@ -104,7 +103,8 @@ Post.to_xlsx(instances: posts, spreadsheet_columns: Proc.new{|instance|
|
|
|
104
103
|
:published_at, # uses the method name as header title Einstance. 'Published At'
|
|
105
104
|
['# of Views', :number_of_views, :float],
|
|
106
105
|
['Rating', :rating],
|
|
107
|
-
['Category/Tags', "#{instance.category.name} - #{instance.tags.collect(&:name).join(', ')}"]
|
|
106
|
+
['Category/Tags', "#{instance.category.name} - #{instance.tags.collect(&:name).join(', ')}"],
|
|
107
|
+
['URL', :url, (val.start_with?("http") ? :hyperlink : :string)],
|
|
108
108
|
]
|
|
109
109
|
})
|
|
110
110
|
```
|
|
@@ -190,20 +190,16 @@ File.open('path/to/multi_sheet_file.xlsx', 'w+b') do |f|
|
|
|
190
190
|
end
|
|
191
191
|
```
|
|
192
192
|
|
|
193
|
-
See this file for more details: https://github.com/westonganger/spreadsheet_architect/blob/master/test/spreadsheet_architect/multi_sheet_test.rb
|
|
194
|
-
|
|
195
193
|
### ODS
|
|
196
194
|
```ruby
|
|
197
195
|
ods_spreadsheet = SpreadsheetArchitect.to_rodf_spreadsheet({headers: headers, data: data})
|
|
198
196
|
ods_spreadsheet = SpreadsheetArchitect.to_rodf_spreadsheet({headers: headers, data: data}, ods_spreadsheet)
|
|
199
197
|
|
|
200
198
|
File.open('path/to/multi_sheet_file.ods', 'w+b') do |f|
|
|
201
|
-
f.write ods_spreadsheet
|
|
199
|
+
f.write ods_spreadsheet.bytes
|
|
202
200
|
end
|
|
203
201
|
```
|
|
204
202
|
|
|
205
|
-
See this file for more details: https://github.com/westonganger/spreadsheet_architect/blob/master/test/spreadsheet_architect/multi_sheet_test.rb
|
|
206
|
-
|
|
207
203
|
# Methods
|
|
208
204
|
|
|
209
205
|
## `to_xlsx(options={})`
|
|
@@ -215,17 +211,20 @@ See this file for more details: https://github.com/westonganger/spreadsheet_arch
|
|
|
215
211
|
|**spreadsheet_columns**<br>*Proc/Symbol/String*| Use this option to override or define the spreadsheet columns. Normally, if this option is not specified and are using the instances option/ActiveRecord relation, it uses the classes custom `spreadsheet_columns` method or any custom defaults defined.<br>If neither of those and is an ActiveRecord model, then it will falls back to the models `self.column_names` | Cannot be used with the `:data` option.<br><br>If a Proc value is passed it will be evaluated on the instance object.<br><br>If a Symbol or String value is passed then it will search the instance for a method name that matches and call it. |
|
|
216
212
|
|**headers**<br>*Array / 2D Array*| |Data for the header row cells. If using on a class/relation, this defaults to the ones provided via `spreadsheet_columns`. Pass `false` to skip the header row. |
|
|
217
213
|
|**sheet_name**<br>*String*|`Sheet1`||
|
|
218
|
-
|**header_style**<br>*Hash*|`{background_color: "AAAAAA", color: "FFFFFF", align: :center, font_name: 'Arial', font_size: 10, bold: false, italic: false, underline: false}`|See all available style options [here](
|
|
219
|
-
|**row_style**<br>*Hash*|`{background_color: nil, color: "000000", align: :left, font_name: 'Arial', font_size: 10, bold: false, italic: false, underline: false, format_code: nil}`|Styles for non-header rows. See all available style options [here](
|
|
220
|
-
|**column_styles**<br>*Array*||[See this example for usage](
|
|
221
|
-
|**range_styles**<br>*Array*||[See this example for usage](
|
|
222
|
-
|**conditional_row_styles**<br>*Array*||[See this example for usage](
|
|
223
|
-
|**merges**<br>*Array*||Merge cells. [See this example for usage](
|
|
224
|
-
|**borders**<br>*Array*||[See this example for usage](
|
|
225
|
-
|**column_types**<br>*Array*||Valid types for XLSX are :string, :integer, :float, :date, :time, :boolean, nil = auto determine
|
|
214
|
+
|**header_style**<br>*Hash*|`{background_color: "AAAAAA", color: "FFFFFF", align: :center, font_name: 'Arial', font_size: 10, bold: false, italic: false, underline: false}`|See all available style options [here](./docs/axlsx_style_reference.md)|
|
|
215
|
+
|**row_style**<br>*Hash*|`{background_color: nil, color: "000000", align: :left, font_name: 'Arial', font_size: 10, bold: false, italic: false, underline: false, format_code: nil}`|Styles for non-header rows. See all available style options [here](./docs/axlsx_style_reference.md)|
|
|
216
|
+
|**column_styles**<br>*Array*||[See this example for usage](./test/unit/kitchen_sink_test.rb)|
|
|
217
|
+
|**range_styles**<br>*Array*||[See this example for usage](./test/unit/kitchen_sink_test.rb)|
|
|
218
|
+
|**conditional_row_styles**<br>*Array*||[See this example for usage](./test/unit/kitchen_sink_test.rb). The if/unless proc will called with the following args: `row_index`, `row_data`|
|
|
219
|
+
|**merges**<br>*Array*||Merge cells. [See this example for usage](./test/unit/kitchen_sink_test.rb). Warning merges cannot overlap eachother, if you attempt to do so Excel will claim your spreadsheet is corrupt and refuse to open your spreadsheet.|
|
|
220
|
+
|**borders**<br>*Array*||[See this example for usage](./test/unit/kitchen_sink_test.rb)|
|
|
221
|
+
|**column_types**<br>*Array*||Valid types for XLSX are :string, :integer, :float, :date, :time, :boolean, :hyperlink, nil = auto determine. You may also pass a Proc which evaluates to any of the valid types, for example `->(cell_val){ cell_val.start_with?('http') ? :hyperlink : :string }`|
|
|
226
222
|
|**column_widths**<br>*Array*||Sometimes you may want explicit column widths. Use nil if you want a column to autofit again.|
|
|
227
223
|
|**freeze_headers**<br>*Boolean*||Make all header rows frozen/fixed so they do not scroll.|
|
|
228
|
-
|**freeze**<br>*
|
|
224
|
+
|**freeze**<br>*Hash*||Make all specified row and/or column frozen/fixed so they do not scroll. See [example usage](./test/unit/xlsx_freeze_test.rb)|
|
|
225
|
+
|**skip_defaults**<br>*Boolean*|`false`|Removes defaults and default styles. Particularily useful for heavily customized spreadsheets where the default styles get in the way.|
|
|
226
|
+
|**escape_formulas**<br>*Boolean* or *Array*|`true`|Pass a single boolean to apply to all cells, or an array of booleans to control column-by-column. Advisable to be set true when involved with untrusted user input. See [an example of the underlying functionality](https://github.com/caxlsx/caxlsx/blob/master/examples/escape_formula_example.md). NOTE: Header row cells are not escaped. |
|
|
227
|
+
|**use_zero_based_row_index**<br>*Boolean*|`false`|Allows you to use zero-based row indexes when defining `range_styles`, `merges`, etc. Recomended to set this option for the whole project rather than per call. The original reason it was designed to be 1-based is because spreadsheet row numbers actually start with 1.|
|
|
229
228
|
|
|
230
229
|
## `to_axlsx_spreadsheet(options={}, axlsx_package_to_join=nil)`
|
|
231
230
|
Same options as `to_xlsx`
|
|
@@ -241,7 +240,8 @@ Same options as `to_xlsx`
|
|
|
241
240
|
|**sheet_name**<br>*String*|`Sheet1`||
|
|
242
241
|
|**header_style**<br>*Hash*|`{background_color: "AAAAAA", color: "FFFFFF", align: :center, font_size: 10, bold: true}`|Note: Currently ODS only supports these options|
|
|
243
242
|
|**row_style**<br>*Hash*|`{background_color: nil, color: "000000", align: :left, font_size: 10, bold: false}`|Styles for non-header rows. Currently ODS only supports these options|
|
|
244
|
-
|**column_types**<br>*Array*||Valid types for ODS are :string, :float, :date, :time, :boolean, nil = auto determine. Due to [RODF Issue #19](https://github.com/thiagoarrais/rodf/issues/19), :date/:time will be converted to :string |
|
|
243
|
+
|**column_types**<br>*Array*||Valid types for ODS are :string, :float, :date, :time, :boolean, :hyperlink, nil = auto determine. Due to [RODF Issue #19](https://github.com/thiagoarrais/rodf/issues/19), :date/:time will be converted to :string. You may also pass a Proc which evaluates to any of the valid types, for example `->(cell_val){ cell_val.start_with?('http') ? :hyperlink : :string }` |
|
|
244
|
+
|**skip_defaults**<br>*Boolean*|`false`|Skip defaults and default styles. Particularily useful for heavily customized spreadsheets where the default styles get in the way.|
|
|
245
245
|
|
|
246
246
|
## `to_rodf_spreadsheet(options={}, spreadsheet_to_join=nil)`
|
|
247
247
|
Same options as `to_ods`
|
|
@@ -302,15 +302,16 @@ SpreadsheetArchitect.default_options = {
|
|
|
302
302
|
merges: [],
|
|
303
303
|
borders: [],
|
|
304
304
|
column_types: [],
|
|
305
|
+
use_zero_based_row_index: false,
|
|
305
306
|
}
|
|
306
307
|
```
|
|
307
308
|
|
|
308
309
|
# Kitchen Sink Examples with Styling for XLSX and ODS
|
|
309
|
-
See this example:
|
|
310
|
+
See this example: [test/unit/kitchen_sink_test.rb](./test/unit/kitchen_sink_test.rb)
|
|
310
311
|
|
|
311
312
|
# Axlsx Style Reference
|
|
312
313
|
|
|
313
|
-
I have compiled a list of all available style options for axlsx here:
|
|
314
|
+
I have compiled a list of all available style options for axlsx here: [docs/axlsx_style_reference.md](./docs/axlsx_style_reference.md)
|
|
314
315
|
|
|
315
316
|
# Testing / Validating your Spreadsheets
|
|
316
317
|
|
|
@@ -328,7 +329,3 @@ At this time the spreadsheets generated by the test suite are manually inspected
|
|
|
328
329
|
# Credits
|
|
329
330
|
|
|
330
331
|
Created & Maintained by [Weston Ganger](https://westonganger.com) - [@westonganger](https://github.com/westonganger)
|
|
331
|
-
|
|
332
|
-
For any consulting or contract work please contact me via my company website: [Solid Foundation Web Development](https://solidfoundationwebdev.com)
|
|
333
|
-
|
|
334
|
-
[](https://solidfoundationwebdev.com)
|
|
@@ -11,7 +11,7 @@ module SpreadsheetArchitect
|
|
|
11
11
|
opts = SpreadsheetArchitect::Utils.get_options(opts, self)
|
|
12
12
|
options = SpreadsheetArchitect::Utils.get_cell_data(opts, self)
|
|
13
13
|
|
|
14
|
-
if options[:column_types] && !(options[:column_types].compact.collect(&:to_sym) - SpreadsheetArchitect::ODS_COLUMN_TYPES).empty?
|
|
14
|
+
if options[:column_types] && !(options[:column_types].compact.reject{|x| x.is_a?(Proc) }.collect(&:to_sym) - SpreadsheetArchitect::ODS_COLUMN_TYPES).empty?
|
|
15
15
|
raise SpreadsheetArchitect::Exceptions::ArgumentError.new("Invalid column type. Valid ODS values are #{SpreadsheetArchitect::ODS_COLUMN_TYPES}")
|
|
16
16
|
end
|
|
17
17
|
|
|
@@ -21,7 +21,7 @@ module SpreadsheetArchitect
|
|
|
21
21
|
|
|
22
22
|
spreadsheet.office_style :header_style, family: :cell do
|
|
23
23
|
if options[:header_style]
|
|
24
|
-
SpreadsheetArchitect::Utils.
|
|
24
|
+
SpreadsheetArchitect::Utils::ODS.convert_styles(options[:header_style]).each do |prop, styles|
|
|
25
25
|
styles.each do |k,v|
|
|
26
26
|
property prop.to_sym, k => v
|
|
27
27
|
end
|
|
@@ -31,7 +31,7 @@ module SpreadsheetArchitect
|
|
|
31
31
|
|
|
32
32
|
spreadsheet.office_style :row_style, family: :cell do
|
|
33
33
|
if options[:row_style]
|
|
34
|
-
SpreadsheetArchitect::Utils.
|
|
34
|
+
SpreadsheetArchitect::Utils::ODS.convert_styles(options[:row_style]).each do |prop, styles|
|
|
35
35
|
styles.each do |k,v|
|
|
36
36
|
property prop.to_sym, k => v
|
|
37
37
|
end
|
|
@@ -54,15 +54,25 @@ module SpreadsheetArchitect
|
|
|
54
54
|
row do
|
|
55
55
|
row_data.each_with_index do |val, i|
|
|
56
56
|
if options[:column_types]
|
|
57
|
-
|
|
57
|
+
provided_column_type = options[:column_types][i]
|
|
58
|
+
|
|
59
|
+
if provided_column_type.is_a?(Proc)
|
|
60
|
+
provided_column_type = provided_column_type.call(val)
|
|
61
|
+
end
|
|
58
62
|
end
|
|
59
63
|
|
|
60
|
-
|
|
61
|
-
|
|
62
|
-
|
|
64
|
+
type = SpreadsheetArchitect::Utils::ODS.get_cell_type(val, provided_column_type)
|
|
65
|
+
|
|
66
|
+
cell_opts = {
|
|
67
|
+
style: :row_style,
|
|
68
|
+
type: type,
|
|
69
|
+
}
|
|
70
|
+
|
|
71
|
+
if provided_column_type == :hyperlink
|
|
72
|
+
cell_opts[:url] = val
|
|
63
73
|
end
|
|
64
74
|
|
|
65
|
-
cell
|
|
75
|
+
cell(val, **cell_opts)
|
|
66
76
|
end
|
|
67
77
|
end
|
|
68
78
|
end
|
|
@@ -1,5 +1,4 @@
|
|
|
1
1
|
require 'axlsx'
|
|
2
|
-
require 'axlsx_styler'
|
|
3
2
|
|
|
4
3
|
require 'spreadsheet_architect/axlsx_string_width_patch'
|
|
5
4
|
|
|
@@ -14,7 +13,7 @@ module SpreadsheetArchitect
|
|
|
14
13
|
opts = SpreadsheetArchitect::Utils.get_options(opts, self)
|
|
15
14
|
options = SpreadsheetArchitect::Utils.get_cell_data(opts, self)
|
|
16
15
|
|
|
17
|
-
if options[:column_types] && !(options[:column_types].compact.collect(&:to_sym) - SpreadsheetArchitect::XLSX_COLUMN_TYPES).empty?
|
|
16
|
+
if options[:column_types] && !(options[:column_types].compact.reject{|x| x.is_a?(Proc) }.collect(&:to_sym) - SpreadsheetArchitect::XLSX_COLUMN_TYPES).empty?
|
|
18
17
|
raise SpreadsheetArchitect::Exceptions::ArgumentError.new("Invalid column type. Valid XLSX values are #{SpreadsheetArchitect::XLSX_COLUMN_TYPES}")
|
|
19
18
|
end
|
|
20
19
|
|
|
@@ -79,16 +78,27 @@ module SpreadsheetArchitect
|
|
|
79
78
|
|
|
80
79
|
types = []
|
|
81
80
|
styles = []
|
|
82
|
-
|
|
83
|
-
|
|
81
|
+
hyperlink_cell_indexes = []
|
|
82
|
+
|
|
83
|
+
row_data.each_with_index do |val,i|
|
|
84
|
+
if (val.respond_to?(:empty) ? val.empty? : val.nil?)
|
|
84
85
|
types[i] = nil
|
|
85
86
|
styles[i] = row_style_index
|
|
86
87
|
else
|
|
87
88
|
if options[:column_types]
|
|
88
|
-
|
|
89
|
+
provided_column_type = options[:column_types][i]
|
|
90
|
+
|
|
91
|
+
if provided_column_type.is_a?(Proc)
|
|
92
|
+
provided_column_type = provided_column_type.call(val)
|
|
93
|
+
end
|
|
89
94
|
end
|
|
90
95
|
|
|
91
|
-
|
|
96
|
+
if provided_column_type == :hyperlink
|
|
97
|
+
hyperlink_cell_indexes << i
|
|
98
|
+
row_data[i] = val.to_s
|
|
99
|
+
end
|
|
100
|
+
|
|
101
|
+
types[i] = SpreadsheetArchitect::Utils::XLSX.get_type(val, provided_column_type)
|
|
92
102
|
|
|
93
103
|
if [:date, :time].include?(types[i])
|
|
94
104
|
if types[i] == :date
|
|
@@ -104,7 +114,12 @@ module SpreadsheetArchitect
|
|
|
104
114
|
end
|
|
105
115
|
end
|
|
106
116
|
|
|
107
|
-
sheet.add_row row_data, style: styles, types: types
|
|
117
|
+
sheet.add_row row_data, style: styles, types: types, escape_formulas: options[:escape_formulas]
|
|
118
|
+
|
|
119
|
+
hyperlink_cell_indexes.each do |cell_index|
|
|
120
|
+
cell_ref = "#{SpreadsheetArchitect::Utils::XLSX::COL_NAMES[cell_index]}#{row_index+1}"
|
|
121
|
+
sheet.add_hyperlink location: row_data[cell_index], ref: cell_ref
|
|
122
|
+
end
|
|
108
123
|
|
|
109
124
|
if options[:conditional_row_styles]
|
|
110
125
|
options[:conditional_row_styles] = SpreadsheetArchitect::Utils.hash_array_symbolize_keys(options[:conditional_row_styles])
|
|
@@ -133,12 +148,12 @@ module SpreadsheetArchitect
|
|
|
133
148
|
|
|
134
149
|
options[:borders].each do |x|
|
|
135
150
|
if x[:range].is_a?(Hash)
|
|
136
|
-
x[:range] = SpreadsheetArchitect::Utils::XLSX.range_hash_to_str(x[:range], max_row_length, num_rows)
|
|
151
|
+
x[:range] = SpreadsheetArchitect::Utils::XLSX.range_hash_to_str(x[:range], max_row_length, num_rows, use_zero_based_row_index: options[:use_zero_based_row_index])
|
|
137
152
|
else
|
|
138
153
|
SpreadsheetArchitect::Utils::XLSX.verify_range(x[:range], num_rows)
|
|
139
154
|
end
|
|
140
155
|
|
|
141
|
-
sheet.add_border x[:range], (x[:border_styles] || x[:styles])
|
|
156
|
+
sheet.add_border x[:range], (x[:border_styles] || x[:styles] || Axlsx::Border::EDGES)
|
|
142
157
|
end
|
|
143
158
|
end
|
|
144
159
|
|
|
@@ -182,7 +197,7 @@ module SpreadsheetArchitect
|
|
|
182
197
|
styles = SpreadsheetArchitect::Utils::XLSX.convert_styles_to_axlsx(x[:styles])
|
|
183
198
|
|
|
184
199
|
if x[:range].is_a?(Hash)
|
|
185
|
-
x[:range] = SpreadsheetArchitect::Utils::XLSX.range_hash_to_str(x[:range], max_row_length, num_rows)
|
|
200
|
+
x[:range] = SpreadsheetArchitect::Utils::XLSX.range_hash_to_str(x[:range], max_row_length, num_rows, use_zero_based_row_index: options[:use_zero_based_row_index])
|
|
186
201
|
else
|
|
187
202
|
SpreadsheetArchitect::Utils::XLSX.verify_range(x[:range], num_rows)
|
|
188
203
|
end
|
|
@@ -196,7 +211,7 @@ module SpreadsheetArchitect
|
|
|
196
211
|
|
|
197
212
|
options[:merges].each do |x|
|
|
198
213
|
if x[:range].is_a?(Hash)
|
|
199
|
-
x[:range] = SpreadsheetArchitect::Utils::XLSX.range_hash_to_str(x[:range], max_row_length, num_rows)
|
|
214
|
+
x[:range] = SpreadsheetArchitect::Utils::XLSX.range_hash_to_str(x[:range], max_row_length, num_rows, use_zero_based_row_index: options[:use_zero_based_row_index])
|
|
200
215
|
else
|
|
201
216
|
SpreadsheetArchitect::Utils::XLSX.verify_range(x[:range], num_rows)
|
|
202
217
|
end
|
|
@@ -212,33 +227,62 @@ module SpreadsheetArchitect
|
|
|
212
227
|
end
|
|
213
228
|
|
|
214
229
|
elsif options[:freeze]
|
|
215
|
-
options[:freeze]
|
|
230
|
+
case options[:freeze][:type].to_s
|
|
231
|
+
when "split_panes"
|
|
232
|
+
options[:freeze][:state] == "split"
|
|
233
|
+
when "frozen", "freeze"
|
|
234
|
+
options[:freeze][:state] == "frozen"
|
|
235
|
+
end
|
|
236
|
+
|
|
237
|
+
if options[:freeze][:rows]
|
|
238
|
+
options[:freeze][:row] ||= options[:freeze][:rows]
|
|
239
|
+
end
|
|
240
|
+
|
|
241
|
+
if options[:freeze][:columns]
|
|
242
|
+
options[:freeze][:column] ||= options[:freeze][:columns]
|
|
243
|
+
end
|
|
244
|
+
|
|
245
|
+
if options[:freeze][:row] == :all
|
|
246
|
+
options[:freeze][:row] = nil
|
|
247
|
+
elsif options[:freeze][:row].is_a?(Range)
|
|
248
|
+
options[:freeze][:row] = options[:freeze][:row].last
|
|
249
|
+
end
|
|
250
|
+
|
|
251
|
+
if options[:freeze][:column] == :all
|
|
252
|
+
options[:freeze][:column] = nil
|
|
253
|
+
elsif options[:freeze][:column].is_a?(Range)
|
|
254
|
+
options[:freeze][:column] = options[:freeze][:column].last
|
|
255
|
+
end
|
|
256
|
+
|
|
257
|
+
if !options[:freeze][:row] && !options[:freeze][:column]
|
|
258
|
+
raise SpreadsheetArchitect::Exceptions::ArgumentError.new("Missing required :row or :column value in the :freeze option hash")
|
|
259
|
+
elsif options[:freeze][:row] && !options[:freeze][:row].is_a?(Integer)
|
|
260
|
+
raise SpreadsheetArchitect::Exceptions::ArgumentError.new("Invalid :row value provided for in :freeze option hash, must be an Integer")
|
|
261
|
+
elsif options[:freeze][:column] && !options[:freeze][:column].is_a?(Integer)
|
|
262
|
+
raise SpreadsheetArchitect::Exceptions::ArgumentError.new("Invalid :column value provided for in :freeze option hash, must be an Integer")
|
|
263
|
+
end
|
|
216
264
|
|
|
217
265
|
sheet.sheet_view.pane do |pane|
|
|
218
|
-
pane.state = :frozen
|
|
266
|
+
pane.state = (options[:freeze][:state] || :frozen).to_sym ### Other options are :split and :frozen_split
|
|
219
267
|
|
|
220
|
-
|
|
221
|
-
|
|
222
|
-
# Axlsx.validate_pane_type(options[:freeze][:active_pane])
|
|
223
|
-
# pane.active_pane = options[:freeze][:active_pane]
|
|
224
|
-
#else
|
|
225
|
-
# pane.active_pane = :bottom_right
|
|
226
|
-
#end
|
|
227
|
-
|
|
228
|
-
if !options[:freeze][:rows]
|
|
229
|
-
raise SpreadsheetArchitect::Exceptions::ArgumentError.new("The :rows key must be specified in the :freeze option hash")
|
|
230
|
-
elsif options[:freeze][:rows].is_a?(Range)
|
|
231
|
-
pane.y_split = options[:freeze][:rows].count
|
|
232
|
-
else
|
|
233
|
-
pane.y_split = 1
|
|
268
|
+
if options[:freeze][:active_pane]
|
|
269
|
+
pane.active_pane = options[:freeze][:active_pane].to_sym
|
|
234
270
|
end
|
|
235
271
|
|
|
236
|
-
if options[:freeze][:
|
|
237
|
-
|
|
238
|
-
|
|
239
|
-
|
|
240
|
-
|
|
272
|
+
if options[:freeze][:top_left_cell]
|
|
273
|
+
pane.top_left_cell = options[:freeze][:top_left_cell]
|
|
274
|
+
end
|
|
275
|
+
|
|
276
|
+
if options[:freeze][:row]
|
|
277
|
+
if options[:use_zero_based_row_index]
|
|
278
|
+
options[:freeze][:row] += 1
|
|
241
279
|
end
|
|
280
|
+
|
|
281
|
+
pane.y_split = options[:freeze][:row]
|
|
282
|
+
end
|
|
283
|
+
|
|
284
|
+
if options[:freeze][:column]
|
|
285
|
+
pane.x_split = options[:freeze][:column]
|
|
242
286
|
end
|
|
243
287
|
end
|
|
244
288
|
end
|
|
@@ -14,17 +14,27 @@ module SpreadsheetArchitect
|
|
|
14
14
|
end
|
|
15
15
|
|
|
16
16
|
class InvalidRangeError < ArgumentError
|
|
17
|
-
def initialize(type, range)
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
|
|
26
|
-
|
|
17
|
+
def initialize(type, range, message: nil)
|
|
18
|
+
default_msg = "Invalid range `#{range}` passed"
|
|
19
|
+
|
|
20
|
+
if message.nil?
|
|
21
|
+
case type
|
|
22
|
+
when :missing_range_keys
|
|
23
|
+
message = "Missing :rows or :columns key"
|
|
24
|
+
when :format
|
|
25
|
+
message = "Format must be as follows: A1:D4"
|
|
26
|
+
when :type
|
|
27
|
+
message = "Valid types are Hash and String"
|
|
28
|
+
end
|
|
27
29
|
end
|
|
30
|
+
|
|
31
|
+
super([default_msg, message].compact.join(". "))
|
|
32
|
+
end
|
|
33
|
+
end
|
|
34
|
+
|
|
35
|
+
class InvalidRangeValue < ArgumentError
|
|
36
|
+
def initialize(type, range)
|
|
37
|
+
super("Invalid range `#{range}` passed. Some of the :#{type} specified are either an invalid value or are greater than the total number of #{type}")
|
|
28
38
|
end
|
|
29
39
|
end
|
|
30
40
|
|
|
@@ -34,9 +44,16 @@ module SpreadsheetArchitect
|
|
|
34
44
|
end
|
|
35
45
|
end
|
|
36
46
|
|
|
37
|
-
class
|
|
38
|
-
def initialize(
|
|
39
|
-
|
|
47
|
+
class InvalidRangeOptionError < ArgumentError
|
|
48
|
+
def initialize(key, opt)
|
|
49
|
+
default_msg = "Invalid :#{key} option for `#{opt}`"
|
|
50
|
+
|
|
51
|
+
case key
|
|
52
|
+
when :columns, :rows
|
|
53
|
+
message = ":#{key} can be an integer, range, or :all"
|
|
54
|
+
end
|
|
55
|
+
|
|
56
|
+
super([default_msg, message].compact.join(". "))
|
|
40
57
|
end
|
|
41
58
|
end
|
|
42
59
|
|