pilipinas 1.0.0 → 1.1.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 +79 -0
- data/Gemfile.lock +2 -2
- data/README.md +44 -46
- data/lib/pilipinas/db/concerns/static_record.rb +35 -10
- data/lib/pilipinas/testing/rspec.rb +46 -0
- data/lib/pilipinas/version.rb +1 -1
- metadata +3 -1
checksums.yaml
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
---
|
|
2
2
|
SHA256:
|
|
3
|
-
metadata.gz:
|
|
4
|
-
data.tar.gz:
|
|
3
|
+
metadata.gz: 3191d97a140c01be0e95c6f1045d54fbd4e4e4ca0bf84783520d67c865376dee
|
|
4
|
+
data.tar.gz: 8216cefb4c6d5d81af30087d6f13a32f5feb79b729f74c194f00c17da7c37e2e
|
|
5
5
|
SHA512:
|
|
6
|
-
metadata.gz:
|
|
7
|
-
data.tar.gz:
|
|
6
|
+
metadata.gz: 4a917e6a92b3f12506b6cf08e7c09c2cd37a6db31bdf6f8d6fb6cd9b1317fa1f23002e4839829ba023a6aeb80e68f74c92a91feb66bc0c4d6a9c8ed0178209e7
|
|
7
|
+
data.tar.gz: faea923c4f805a2b2cbb43d89676cb66b95c2e9df643f6aedb8125c4d1cd8d1cad1f0a946d39a70a8edac2d165d068ec1e06046d33390d3cff481e60cabeded5
|
data/CHANGELOG.md
ADDED
|
@@ -0,0 +1,79 @@
|
|
|
1
|
+
# Changelog
|
|
2
|
+
|
|
3
|
+
All notable changes to this project will be documented in this file.
|
|
4
|
+
|
|
5
|
+
The format is based on [Keep a Changelog](https://keepachangelog.com/en/1.0.0/),
|
|
6
|
+
and this project adheres to [Semantic Versioning](https://semver.org/spec/v2.0.0.html).
|
|
7
|
+
|
|
8
|
+
---
|
|
9
|
+
|
|
10
|
+
## [1.1.0] - 2026-05-13
|
|
11
|
+
|
|
12
|
+
### Added
|
|
13
|
+
|
|
14
|
+
- `enforce_readonly` class attribute on the `StaticRecord` concern (default: `true`).
|
|
15
|
+
Subclasses can opt out of the read-only guard without stubbing:
|
|
16
|
+
```ruby
|
|
17
|
+
class Locations::Barangay < Pilipinas::Db::Barangay
|
|
18
|
+
self.enforce_readonly = false
|
|
19
|
+
end
|
|
20
|
+
```
|
|
21
|
+
- `lib/pilipinas/testing/rspec.rb` — a ready-made RSpec helper that disables
|
|
22
|
+
the read-only guard on all four DB models for the entire test suite.
|
|
23
|
+
Require it once in `rails_helper.rb`:
|
|
24
|
+
```ruby
|
|
25
|
+
require 'pilipinas/testing/rspec'
|
|
26
|
+
```
|
|
27
|
+
- Spec coverage for `StaticRecord` — 8 examples covering default behaviour,
|
|
28
|
+
`enforce_readonly = false`, subclass inheritance, and class-level isolation.
|
|
29
|
+
|
|
30
|
+
### Changed
|
|
31
|
+
|
|
32
|
+
- `readonly?` now gates on `self.class.enforce_readonly && !new_record?` instead
|
|
33
|
+
of unconditionally returning `!new_record?`.
|
|
34
|
+
|
|
35
|
+
---
|
|
36
|
+
|
|
37
|
+
## [1.0.0] - 2026-05-12
|
|
38
|
+
|
|
39
|
+
Complete rewrite of the gem. Zero runtime dependencies.
|
|
40
|
+
|
|
41
|
+
### Added
|
|
42
|
+
|
|
43
|
+
- In-memory layer with thread-safe `Pilipinas::Cache` (Mutex + double-checked
|
|
44
|
+
locking) and O(1) look-ups via separate code/name hash indices.
|
|
45
|
+
- Immutable value objects — every entity instance is frozen.
|
|
46
|
+
- `Pilipinas::Region`, `Province`, `City`, `Barangay` with `.all`, `.count`,
|
|
47
|
+
`.first`, `.last`, `.find_by`, `.find_by_code`, `.find_by_name`.
|
|
48
|
+
- Hierarchy traversal: `region.provinces`, `province.cities`, `city.barangays`.
|
|
49
|
+
- Optional ActiveRecord layer (`Pilipinas::Db::*`) with memory-efficient scopes
|
|
50
|
+
(`.lite`, `.by_code`, `.by_name`, `.find_lite_by_code`, `.find_lite_by_name`).
|
|
51
|
+
- `StaticRecord` concern: disables STI, adds lean SELECT scopes, enforces
|
|
52
|
+
read-only on persisted records.
|
|
53
|
+
- Migration generator (`rails generate pilipinas:migration`) and
|
|
54
|
+
`rake pilipinas:load` seeding task.
|
|
55
|
+
- Full RSpec suite (57 examples).
|
|
56
|
+
- GitHub Actions CI pipeline.
|
|
57
|
+
|
|
58
|
+
### Changed
|
|
59
|
+
|
|
60
|
+
- Requires Ruby ≥ 3.4 (developed against Ruby 4.0).
|
|
61
|
+
- Removed all runtime gem dependencies (previously depended on `yaml_db` and
|
|
62
|
+
others).
|
|
63
|
+
|
|
64
|
+
---
|
|
65
|
+
|
|
66
|
+
## [0.0.1] - 2019-01-26
|
|
67
|
+
|
|
68
|
+
### Added
|
|
69
|
+
|
|
70
|
+
- Initial release.
|
|
71
|
+
- YAML data for Philippine regions, provinces, cities, and barangays.
|
|
72
|
+
- ActiveRecord models backed by `pilipinas_*` tables.
|
|
73
|
+
- Migration template and Rake loader task.
|
|
74
|
+
- Rails generator for migrations.
|
|
75
|
+
- Railtie for automatic Rake task loading in Rails apps.
|
|
76
|
+
|
|
77
|
+
[1.1.0]: https://github.com/denmarkmeralpis/pilipinas/compare/v1.0.0...v1.1.0
|
|
78
|
+
[1.0.0]: https://github.com/denmarkmeralpis/pilipinas/compare/v0.0.1...v1.0.0
|
|
79
|
+
[0.0.1]: https://github.com/denmarkmeralpis/pilipinas/releases/tag/v0.0.1
|
data/Gemfile.lock
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
PATH
|
|
2
2
|
remote: .
|
|
3
3
|
specs:
|
|
4
|
-
pilipinas (1.
|
|
4
|
+
pilipinas (1.1.0)
|
|
5
5
|
|
|
6
6
|
GEM
|
|
7
7
|
remote: https://rubygems.org/
|
|
@@ -295,7 +295,7 @@ CHECKSUMS
|
|
|
295
295
|
nokogiri (1.19.3-x86_64-linux-musl) sha256=248c906d2166eca5efb56d52fdee5f9a1f51d69a72e2b64fdac647b4ce39ea3f
|
|
296
296
|
parallel (2.1.0) sha256=b35258865c2e31134c5ecb708beaaf6772adf9d5efae28e93e99260877b09356
|
|
297
297
|
parser (3.3.11.1) sha256=d17ace7aabe3e72c3cc94043714be27cc6f852f104d81aa284c2281aecc65d54
|
|
298
|
-
pilipinas (1.
|
|
298
|
+
pilipinas (1.1.0)
|
|
299
299
|
pp (0.6.3) sha256=2951d514450b93ccfeb1df7d021cae0da16e0a7f95ee1e2273719669d0ab9df6
|
|
300
300
|
prettyprint (0.2.0) sha256=2bc9e15581a94742064a3cc8b0fb9d45aae3d03a1baa6ef80922627a0766f193
|
|
301
301
|
prism (1.9.0) sha256=7b530c6a9f92c24300014919c9dcbc055bf4cdf51ec30aed099b06cd6674ef85
|
data/README.md
CHANGED
|
@@ -18,6 +18,8 @@ Region → Province → City / Municipality → Barangay
|
|
|
18
18
|
- **O(1) look-ups** — separate hash indices keyed by code and by name; no linear scans.
|
|
19
19
|
- **Immutable value objects** — every entity instance is frozen. Safe to share across threads and fibers without copying.
|
|
20
20
|
- **Optional ActiveRecord integration** — a migration generator and Rake task seed the four `pilipinas_*` tables from the bundled YAML data.
|
|
21
|
+
- **Read-only by default** — persisted AR model instances raise `ActiveRecord::ReadOnlyRecord` on accidental writes; opt out per-class via `enforce_readonly = false`.
|
|
22
|
+
- **Test helper included** — `require 'pilipinas/testing/rspec'` disables the read-only guard for the entire RSpec suite with one line.
|
|
21
23
|
- **Ruby ≥ 3.4** required; developed against Ruby 4.0.
|
|
22
24
|
|
|
23
25
|
---
|
|
@@ -184,6 +186,48 @@ province.cities # has_many association
|
|
|
184
186
|
|
|
185
187
|
> **Note:** The AR models are auto-loaded and require `activerecord` to be available.
|
|
186
188
|
|
|
189
|
+
### Read-only behaviour
|
|
190
|
+
|
|
191
|
+
All four `Pilipinas::Db::*` models are **read-only by default**. Any attempt to call `update!`, `save`, or `destroy` on a persisted record raises `ActiveRecord::ReadOnlyRecord`. This is intentional — the pilipinas tables are static reference data that should never be mutated after seeding.
|
|
192
|
+
|
|
193
|
+
New (unsaved) records are always writable, so `create!` works normally in the Loader and in test factories.
|
|
194
|
+
|
|
195
|
+
#### Opting a subclass out of read-only enforcement
|
|
196
|
+
|
|
197
|
+
If your application inherits from a Pilipinas DB model and legitimately needs write access, set `enforce_readonly` to `false` on the subclass:
|
|
198
|
+
|
|
199
|
+
```ruby
|
|
200
|
+
class Locations::Barangay < Pilipinas::Db::Barangay
|
|
201
|
+
self.enforce_readonly = false
|
|
202
|
+
end
|
|
203
|
+
```
|
|
204
|
+
|
|
205
|
+
This does not affect the parent class or any other model.
|
|
206
|
+
|
|
207
|
+
---
|
|
208
|
+
|
|
209
|
+
## Testing
|
|
210
|
+
|
|
211
|
+
The gem ships a ready-made RSpec helper that turns off the read-only guard for the entire test suite — no stubbing required.
|
|
212
|
+
|
|
213
|
+
```ruby
|
|
214
|
+
# spec/rails_helper.rb (or spec/support/pilipinas.rb)
|
|
215
|
+
require 'pilipinas/testing/rspec'
|
|
216
|
+
```
|
|
217
|
+
|
|
218
|
+
This sets `enforce_readonly = false` on all four models (`Region`, `Province`, `City`, `Barangay`) inside a `before(:suite)` hook, so FactoryBot factories, fixtures, and any spec that writes to pilipinas tables work without extra setup.
|
|
219
|
+
|
|
220
|
+
If you only need writable records in a specific context:
|
|
221
|
+
|
|
222
|
+
```ruby
|
|
223
|
+
around do |example|
|
|
224
|
+
Locations::Barangay.enforce_readonly = false
|
|
225
|
+
example.run
|
|
226
|
+
ensure
|
|
227
|
+
Locations::Barangay.enforce_readonly = true
|
|
228
|
+
end
|
|
229
|
+
```
|
|
230
|
+
|
|
187
231
|
---
|
|
188
232
|
|
|
189
233
|
## Advanced
|
|
@@ -238,54 +282,8 @@ The gem is available as open source under the terms of the [MIT License](LICENSE
|
|
|
238
282
|
|
|
239
283
|
## Acknowledgements
|
|
240
284
|
|
|
241
|
-
The geographic data used in this gem is derived from the Philippine Standard Geographic Code (PSGC) published by the Philippine Statistics Authority.
|
|
242
|
-
|
|
243
|
-
|
|
244
|
-
## Installation
|
|
245
|
-
|
|
246
|
-
Add this line to your application's Gemfile:
|
|
247
|
-
|
|
248
|
-
```ruby
|
|
249
|
-
gem 'pilipinas'
|
|
250
|
-
```
|
|
251
|
-
|
|
252
|
-
And then execute:
|
|
253
|
-
|
|
254
|
-
$ bundle
|
|
255
|
-
|
|
256
|
-
Or install it yourself as:
|
|
257
|
-
|
|
258
|
-
$ gem install pilipinas
|
|
259
|
-
|
|
260
|
-
## Usage
|
|
261
|
-
|
|
262
|
-
```ruby
|
|
263
|
-
# All Regions
|
|
264
|
-
Pilipinas::Region.all
|
|
265
|
-
|
|
266
|
-
# All Provinces
|
|
267
|
-
Pilipinas::Province.all
|
|
268
|
-
|
|
269
|
-
# All Cities/Municipalities
|
|
270
|
-
Pilipinas::City.all
|
|
271
|
-
|
|
272
|
-
# All Barangays
|
|
273
|
-
Pilipinas::Barangay.all
|
|
274
|
-
|
|
275
|
-
# Finding record thru find_by_(code/name) method
|
|
276
|
-
region = Pilipinas::Region.find_by_name("REGION V (Bicol Region)")
|
|
277
|
-
|
|
278
|
-
# Get provinces by region
|
|
279
|
-
region.provinces
|
|
280
|
-
```
|
|
281
|
-
## Acknowledgement
|
|
282
|
-
|
|
283
285
|
The data used in this gem is from `gem pinas`. Kudos!
|
|
284
286
|
|
|
285
|
-
## TODO
|
|
286
|
-
|
|
287
|
-
* Add a form helper
|
|
288
|
-
|
|
289
287
|
## Development
|
|
290
288
|
|
|
291
289
|
After checking out the repo, run `bin/setup` to install dependencies. Then, run `rake spec` to run the tests. You can also run `bin/console` for an interactive prompt that will allow you to experiment.
|
|
@@ -25,10 +25,14 @@ module Pilipinas
|
|
|
25
25
|
#
|
|
26
26
|
# == Optimizations applied
|
|
27
27
|
#
|
|
28
|
-
# * +readonly?+ returns +true+ for persisted records
|
|
28
|
+
# * +readonly?+ returns +true+ for persisted records when
|
|
29
|
+
# +enforce_readonly+ is +true+ (the default) — accidental
|
|
29
30
|
# +update!/save!/destroy+ on fetched rows raise
|
|
30
31
|
# +ActiveRecord::ReadOnlyRecord+; new records stay writable so the
|
|
31
32
|
# Loader and test fixtures can still call +create!+.
|
|
33
|
+
# * +enforce_readonly+ class attribute: opt a subclass out of the
|
|
34
|
+
# read-only guard without touching production models — useful in test
|
|
35
|
+
# environments where factories need to write to pilipinas tables.
|
|
32
36
|
# * +self.inheritance_column = :_sti_disabled+: removes STI type-column
|
|
33
37
|
# look-up from every query.
|
|
34
38
|
# * +.lite+ scope: selects only +id+, +location_id+, +code+, +name+ —
|
|
@@ -50,6 +54,11 @@ module Pilipinas
|
|
|
50
54
|
# province.cities # SELECT id, location_id, parent_id, code, name …
|
|
51
55
|
# city.barangays # SELECT id, location_id, parent_id, code, name …
|
|
52
56
|
#
|
|
57
|
+
# @example Opting a subclass out of read-only enforcement (e.g. in tests)
|
|
58
|
+
# class Locations::Barangay < Pilipinas::Db::Barangay
|
|
59
|
+
# self.enforce_readonly = false
|
|
60
|
+
# end
|
|
61
|
+
#
|
|
53
62
|
module StaticRecord
|
|
54
63
|
extend ActiveSupport::Concern
|
|
55
64
|
|
|
@@ -64,6 +73,16 @@ module Pilipinas
|
|
|
64
73
|
# Removes the hidden "type" column check AR performs on every query.
|
|
65
74
|
self.inheritance_column = :_sti_disabled
|
|
66
75
|
|
|
76
|
+
# ── Read-only enforcement ─────────────────────────────────────────
|
|
77
|
+
# Defaults to +true+. Set to +false+ on a subclass (e.g. in a test
|
|
78
|
+
# environment or for a model that legitimately needs write access)
|
|
79
|
+
# without touching production behaviour:
|
|
80
|
+
#
|
|
81
|
+
# class Locations::Barangay < Pilipinas::Db::Barangay
|
|
82
|
+
# self.enforce_readonly = false
|
|
83
|
+
# end
|
|
84
|
+
class_attribute :enforce_readonly, instance_writer: false, default: true
|
|
85
|
+
|
|
67
86
|
# ── Memory-efficient query scopes ─────────────────────────────────
|
|
68
87
|
|
|
69
88
|
# Select only the four columns needed for display and look-up.
|
|
@@ -97,19 +116,25 @@ module Pilipinas
|
|
|
97
116
|
scope :find_lite_by_name, ->(name) { lite.by_name(name).first }
|
|
98
117
|
end
|
|
99
118
|
|
|
100
|
-
#
|
|
101
|
-
#
|
|
102
|
-
# +
|
|
103
|
-
#
|
|
104
|
-
#
|
|
119
|
+
# Guards against accidental writes to static reference data.
|
|
120
|
+
#
|
|
121
|
+
# Returns +true+ (making the record read-only) when both conditions hold:
|
|
122
|
+
# 1. The record is persisted (+new_record?+ is +false+).
|
|
123
|
+
# 2. The class-level +enforce_readonly+ flag is +true+ (the default).
|
|
124
|
+
#
|
|
125
|
+
# New (unsaved) objects are always writable so the Loader and test
|
|
126
|
+
# factories can call +create!+. To allow writes on a subclass — for
|
|
127
|
+
# example in a test environment — set:
|
|
128
|
+
#
|
|
129
|
+
# self.enforce_readonly = false
|
|
105
130
|
#
|
|
106
131
|
# Overriding +readonly?+ is more efficient than an +after_initialize+
|
|
107
|
-
# callback
|
|
108
|
-
#
|
|
132
|
+
# callback: it is only invoked when AR is about to perform a write
|
|
133
|
+
# operation, so it adds zero overhead on read paths.
|
|
109
134
|
#
|
|
110
|
-
# @return [Boolean]
|
|
135
|
+
# @return [Boolean]
|
|
111
136
|
def readonly?
|
|
112
|
-
!new_record?
|
|
137
|
+
self.class.enforce_readonly && !new_record?
|
|
113
138
|
end
|
|
114
139
|
end
|
|
115
140
|
end
|
|
@@ -0,0 +1,46 @@
|
|
|
1
|
+
# frozen_string_literal: true
|
|
2
|
+
|
|
3
|
+
require 'pilipinas'
|
|
4
|
+
|
|
5
|
+
# Pilipinas::Testing::RSpec
|
|
6
|
+
#
|
|
7
|
+
# Optional RSpec helper that disables the read-only guard on all Pilipinas DB
|
|
8
|
+
# models for the duration of the test suite. Require this file once (e.g. in
|
|
9
|
+
# +rails_helper.rb+ or +spec/support/pilipinas.rb+) and FactoryBot factories,
|
|
10
|
+
# fixtures, or any spec that needs to write to pilipinas_* tables will work
|
|
11
|
+
# without stubbing or subclass overrides.
|
|
12
|
+
#
|
|
13
|
+
# == Usage
|
|
14
|
+
#
|
|
15
|
+
# # spec/rails_helper.rb (or spec/support/pilipinas.rb)
|
|
16
|
+
# require 'pilipinas/testing/rspec'
|
|
17
|
+
#
|
|
18
|
+
# == What it does
|
|
19
|
+
#
|
|
20
|
+
# Calls +enforce_readonly = false+ on every Pilipinas DB model inside a
|
|
21
|
+
# +before(:suite)+ hook so the flag is set once, before any example runs.
|
|
22
|
+
# The models remain writable for the entire test process, which is the correct
|
|
23
|
+
# behaviour for a test environment where factories seed the pilipinas_* tables.
|
|
24
|
+
#
|
|
25
|
+
# If you need write access only in a specific context, set the flag manually
|
|
26
|
+
# with an +around+ hook instead of requiring this file globally.
|
|
27
|
+
#
|
|
28
|
+
# == Models affected
|
|
29
|
+
#
|
|
30
|
+
# * Pilipinas::Db::Region
|
|
31
|
+
# * Pilipinas::Db::Province
|
|
32
|
+
# * Pilipinas::Db::City
|
|
33
|
+
# * Pilipinas::Db::Barangay
|
|
34
|
+
|
|
35
|
+
require 'rspec/core'
|
|
36
|
+
|
|
37
|
+
RSpec.configure do |config|
|
|
38
|
+
config.before(:suite) do
|
|
39
|
+
[
|
|
40
|
+
Pilipinas::Db::Region,
|
|
41
|
+
Pilipinas::Db::Province,
|
|
42
|
+
Pilipinas::Db::City,
|
|
43
|
+
Pilipinas::Db::Barangay
|
|
44
|
+
].each { |model| model.enforce_readonly = false }
|
|
45
|
+
end
|
|
46
|
+
end
|
data/lib/pilipinas/version.rb
CHANGED
metadata
CHANGED
|
@@ -1,7 +1,7 @@
|
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
|
2
2
|
name: pilipinas
|
|
3
3
|
version: !ruby/object:Gem::Version
|
|
4
|
-
version: 1.
|
|
4
|
+
version: 1.1.0
|
|
5
5
|
platform: ruby
|
|
6
6
|
authors:
|
|
7
7
|
- Nujian Den Mark Meralpis
|
|
@@ -143,6 +143,7 @@ executables: []
|
|
|
143
143
|
extensions: []
|
|
144
144
|
extra_rdoc_files: []
|
|
145
145
|
files:
|
|
146
|
+
- CHANGELOG.md
|
|
146
147
|
- CODE_OF_CONDUCT.md
|
|
147
148
|
- Gemfile
|
|
148
149
|
- Gemfile.lock
|
|
@@ -1924,6 +1925,7 @@ files:
|
|
|
1924
1925
|
- lib/pilipinas/province.rb
|
|
1925
1926
|
- lib/pilipinas/railtie.rb
|
|
1926
1927
|
- lib/pilipinas/region.rb
|
|
1928
|
+
- lib/pilipinas/testing/rspec.rb
|
|
1927
1929
|
- lib/pilipinas/version.rb
|
|
1928
1930
|
- lib/tasks/pilipinas_tasks.rake
|
|
1929
1931
|
- pilipinas.gemspec
|