Skip to content

Commit

Permalink
refactor(decorator): remove need for magic getter to access localized…
Browse files Browse the repository at this point in the history
… object of a field

BREAKING CHANGE:
- Remove previously deprecated `getUnlocalizedField`.
- Access the localized object of an attribute via `localizedObjects.myField` instead of the magic key `myFieldObject`.
  • Loading branch information
velrest committed Jan 26, 2023
1 parent 65ab213 commit 30d20db
Show file tree
Hide file tree
Showing 7 changed files with 112 additions and 21 deletions.
2 changes: 1 addition & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -74,7 +74,7 @@ If you want to switch locale for only one specific model, you can set
`yourModel.localizedFieldLocale` to the desired locale.

If you want to access the raw data as sent by the backend, you can use
`yourModel.getUnlocalizedField("firstName")`. This will return the raw data.
`yourModel.localizedObjects.firstName`. This will return the raw data.

For example:

Expand Down
3 changes: 2 additions & 1 deletion addon/-private/decorators/localized-attr.js
Original file line number Diff line number Diff line change
Expand Up @@ -60,9 +60,10 @@ export default function (...args) {

// Use the getter and setter for the original property so both
// the Object and the previous getter and setter access the same value.
Object.defineProperty(target, `${name}Object`, {
Object.defineProperty(target, `_${name}`, {
get: getter,
set: setter,
enumerable: false,
});

return attrComputed;
Expand Down
37 changes: 20 additions & 17 deletions addon/-private/models/localized.js
Original file line number Diff line number Diff line change
@@ -1,28 +1,31 @@
import { deprecate } from "@ember/debug";
import { inject as service } from "@ember/service";
import Model from "@ember-data/model";
import { tracked } from "@glimmer/tracking";

export default class LocalizedModel extends Model {
@service intl;
@tracked localizedFieldLocale;
@tracked _localizedObjects;

getUnlocalizedField(field) {
deprecate(
"Usage of `getUnlocalizedField` is deprecated. Access object directly.",
false,
{
id: "ember-localized-model.public-unlocalized",
until: "2.0.0",
url: "https://github.com/projectcaluma/ember-localized-model/pull/101",
for: "ember-localized-model",
since: {
enabled: "1.2.0",
},
}
);

return this[`${field}Object`];
get localizedObjects() {
if (!this._localizedObjects) {
// Save this since the getter will have the
// context from the `_localizedObjects` object.
const context = this;
this._localizedObjects = this.localizedFields.reduce(
(localizedObjects, field) => ({
...localizedObjects,
get [field]() {
return context[`_${field}`];
},
set [field](value) {
context[`_${field}`] = value;
},
}),
{}
);
}
return this._localizedObjects;
}

getFieldLocale() {
Expand Down
2 changes: 1 addition & 1 deletion addon/-private/serializers/localized.js
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,7 @@ export default class ScopeSerializer extends JSONAPISerializer {
const { localizedFields = [] } = snapshot.record;

if (localizedFields.includes(key)) {
json.attributes[key] = snapshot.record.getUnlocalizedField(key);
json.attributes[key] = snapshot.record.localizedObjects[key];
}
}
}
6 changes: 5 additions & 1 deletion tests/dummy/app/controllers/application.js
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,11 @@ export default class ApplicationController extends Controller {
this.intl.setLocale(["en", "de", "fr"]);

const book = this.store.createRecord("book");
book.nameObject = { de: "Der Mond", en: "The Moon", fr: "La Lune" };
book.localizedObjects.name = {
de: "Der Mond",
en: "The Moon",
fr: "La Lune",
};
this.book = book;
}

Expand Down
56 changes: 56 additions & 0 deletions tests/unit/models/localized-test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,56 @@
import { setupIntl, setLocale } from "ember-intl/test-support";
import { setupTest } from "ember-localized-model/tests/helpers/index";
import { module, test } from "qunit";

module("Unit | Model | localized", function (hooks) {
setupTest(hooks);
setupIntl(hooks, "en");

test("it sets value under correct locale", function (assert) {
const store = this.owner.lookup("service:store");
const model = store.createRecord("book");
model.name = "test-en";
setLocale("de");
model.name = "test-de";
setLocale("fr");
model.name = "test-fr";

assert.deepEqual(model.localizedObjects.name, {
de: "test-de",
en: "test-en",
fr: "test-fr",
});

setLocale("en");
assert.strictEqual(model.name, "test-en");
setLocale("de");
assert.strictEqual(model.name, "test-de");
setLocale("fr");
assert.strictEqual(model.name, "test-fr");
});

test("it respects localizedFieldLocale", function (assert) {
const store = this.owner.lookup("service:store");
const model = store.createRecord("book");
model.localizedObjects.name = {
en: "test-en",
de: "test-de",
fr: "test-fr",
};

assert.strictEqual(model.name, "test-en");

model.localizedFieldLocale = "de";
assert.strictEqual(model.name, "test-de");

model.localizedFieldLocale = "fr";
assert.strictEqual(model.name, "test-fr");
});

test("it has localizedObjects", function (assert) {
const store = this.owner.lookup("service:store");
const model = store.createRecord("book");

assert.deepEqual(model.localizedObjects.name, {});
});
});
27 changes: 27 additions & 0 deletions tests/unit/serializers/localized-test.js
Original file line number Diff line number Diff line change
@@ -0,0 +1,27 @@
import { setupIntl } from "ember-intl/test-support";
import { setupTest } from "ember-localized-model/tests/helpers/index";
import { module, test } from "qunit";

module("Unit | Serializer | localized", function (hooks) {
setupTest(hooks);
setupIntl(hooks, "en");

test("it serializes records", function (assert) {
const store = this.owner.lookup("service:store");
const record = store.createRecord("book");
record.name = "test";

const serializedRecord = record.serialize();

assert.deepEqual(serializedRecord, {
data: {
attributes: {
name: {
en: "test",
},
},
type: "books",
},
});
});
});

0 comments on commit 30d20db

Please sign in to comment.