Skip to content

Commit 31e2ae1

Browse files
authored
Merge pull request #10198 from eth3lbert/fix-frontend-deprecated
Fix frontend deprecations
2 parents a093332 + ac1a774 commit 31e2ae1

File tree

14 files changed

+120
-50
lines changed

14 files changed

+120
-50
lines changed

app/components/crate-header.js

Lines changed: 2 additions & 11 deletions
Original file line numberDiff line numberDiff line change
@@ -8,30 +8,21 @@ export default class CrateHeader extends Component {
88
@service session;
99

1010
@alias('loadKeywordsTask.last.value') keywords;
11-
@alias('loadOwnerUserTask.last.value') ownerUser;
1211

1312
constructor() {
1413
super(...arguments);
1514

1615
this.loadKeywordsTask.perform().catch(() => {
1716
// ignore all errors and just don't display keywords if the request fails
1817
});
19-
this.loadOwnerUserTask.perform().catch(() => {
20-
// ignore all errors and just don't display settings if the request fails
21-
});
2218
}
2319

2420
get isOwner() {
25-
let ownerUser = this.ownerUser ?? [];
26-
let currentUserId = this.session.currentUser?.id;
27-
return ownerUser.some(({ id }) => id === currentUserId);
21+
let userId = this.session.currentUser?.id;
22+
return this.args.crate?.hasOwnerUser(userId) ?? false;
2823
}
2924

3025
loadKeywordsTask = task(async () => {
3126
return (await this.args.crate?.keywords) ?? [];
3227
});
33-
34-
loadOwnerUserTask = task(async () => {
35-
return (await this.args.crate?.owner_user) ?? [];
36-
});
3728
}

app/components/crate-sidebar.hbs

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -94,7 +94,7 @@
9494
</div>
9595

9696
{{#unless @crate.categories.isPending}}
97-
{{#if @crate.categories}}
97+
{{#if @crate.categories.length}}
9898
<div>
9999
<h2 local-class="heading">Categories</h2>
100100
<ul local-class="categories">

app/components/version-list/row.js

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -48,7 +48,8 @@ export default class VersionRow extends Component {
4848
}
4949

5050
get isOwner() {
51-
return this.args.version.crate?.owner_user?.findBy('id', this.session.currentUser?.id);
51+
let userId = this.session.currentUser?.id;
52+
return this.args.version.crate.hasOwnerUser(userId);
5253
}
5354

5455
@action setFocused(value) {

app/controllers/crate/settings.js

Lines changed: 11 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -36,10 +36,12 @@ export default class CrateSettingsController extends Controller {
3636

3737
if (owner.kind === 'team') {
3838
this.notifications.success(`Team ${owner.get('display_name')} removed as crate owner`);
39-
this.crate.owner_team.removeObject(owner);
39+
let owner_team = await this.crate.owner_team;
40+
removeOwner(owner_team, owner);
4041
} else {
4142
this.notifications.success(`User ${owner.get('login')} removed as crate owner`);
42-
this.crate.owner_user.removeObject(owner);
43+
let owner_user = await this.crate.owner_user;
44+
removeOwner(owner_user, owner);
4345
}
4446
} catch (error) {
4547
let subject = owner.kind === 'team' ? `team ${owner.get('display_name')}` : `user ${owner.get('login')}`;
@@ -54,3 +56,10 @@ export default class CrateSettingsController extends Controller {
5456
}
5557
});
5658
}
59+
60+
function removeOwner(owners, target) {
61+
let idx = owners.indexOf(target);
62+
if (idx !== -1) {
63+
owners.splice(idx, 1);
64+
}
65+
}

app/controllers/crate/version.js

Lines changed: 9 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -24,13 +24,14 @@ export default class CrateVersionController extends Controller {
2424
this.stackedGraph = false;
2525
}
2626

27-
@alias('downloadsContext.version_downloads.content') downloads;
27+
@alias('loadDownloadsTask.last.value') downloads;
2828
@alias('model.crate') crate;
2929
@alias('model.requestedVersion') requestedVersion;
3030
@alias('model.version') currentVersion;
3131

3232
get isOwner() {
33-
return this.crate.owner_user.findBy('id', this.session.currentUser?.id);
33+
let userId = this.session.currentUser?.id;
34+
return this.crate.hasOwnerUser(userId);
3435
}
3536

3637
@alias('loadReadmeTask.last.value') readme;
@@ -62,4 +63,10 @@ export default class CrateVersionController extends Controller {
6263

6364
return readme;
6465
});
66+
67+
// This task would be `perform()` in setupController
68+
loadDownloadsTask = task(async () => {
69+
let downloads = await this.downloadsContext.version_downloads;
70+
return downloads;
71+
});
6572
}

app/models/crate.js

Lines changed: 42 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -1,8 +1,10 @@
11
import Model, { attr, hasMany } from '@ember-data/model';
2+
import { assert } from '@ember/debug';
23
import { waitForPromise } from '@ember/test-waiters';
34
import { cached } from '@glimmer/tracking';
45

56
import { apiAction } from '@mainmatter/ember-api-actions';
7+
import { task } from 'ember-concurrency';
68

79
export default class Crate extends Model {
810
@attr name;
@@ -35,22 +37,34 @@ export default class Crate extends Model {
3537
@hasMany('dependency', { async: true, inverse: null }) reverse_dependencies;
3638

3739
@cached get versionIdsBySemver() {
38-
let versions = this.versions.toArray() ?? [];
39-
return versions.sort(compareVersionBySemver).map(v => v.id);
40+
let { last } = this.loadVersionsTask;
41+
assert('`loadVersionsTask.perform()` must be called before calling `versionIdsBySemver`', last != null);
42+
let versions = last?.value ?? [];
43+
return versions
44+
.slice()
45+
.sort(compareVersionBySemver)
46+
.map(v => v.id);
4047
}
4148

4249
@cached get versionIdsByDate() {
43-
let versions = this.versions.toArray() ?? [];
44-
return versions.sort(compareVersionByDate).map(v => v.id);
50+
let { last } = this.loadVersionsTask;
51+
assert('`loadVersionsTask.perform()` must be called before calling `versionIdsByDate`', last != null);
52+
let versions = last?.value ?? [];
53+
return versions
54+
.slice()
55+
.sort(compareVersionByDate)
56+
.map(v => v.id);
4557
}
4658

4759
@cached get firstVersionId() {
4860
return this.versionIdsByDate.at(-1);
4961
}
5062

5163
@cached get versionsObj() {
52-
let versions = this.versions.toArray() ?? [];
53-
return Object.fromEntries(versions.map(v => [v.id, v]));
64+
let { last } = this.loadVersionsTask;
65+
assert('`loadVersionsTask.perform()` must be called before calling `versionsObj`', last != null);
66+
let versions = last?.value ?? [];
67+
return Object.fromEntries(versions.slice().map(v => [v.id, v]));
5468
}
5569

5670
@cached get releaseTrackSet() {
@@ -65,10 +79,16 @@ export default class Crate extends Model {
6579
return new Set(map.values());
6680
}
6781

82+
hasOwnerUser(userId) {
83+
let { last } = this.loadOwnerUserTask;
84+
assert('`loadOwnerUserTask.perform()` must be called before calling `hasOwnerUser()`', last != null);
85+
return (last?.value ?? []).some(({ id }) => id === userId);
86+
}
87+
6888
get owners() {
69-
let teams = this.owner_team.toArray() ?? [];
70-
let users = this.owner_user.toArray() ?? [];
71-
return [...teams, ...users];
89+
let { last } = this.loadOwnersTask;
90+
assert('`loadOwnersTask.perform()` must be called before accessing `owners`', last != null);
91+
return last?.value ?? [];
7292
}
7393

7494
async follow() {
@@ -100,6 +120,19 @@ export default class Crate extends Model {
100120
throw response;
101121
}
102122
}
123+
124+
loadOwnerUserTask = task(async () => {
125+
return (await this.owner_user) ?? [];
126+
});
127+
128+
loadOwnersTask = task(async () => {
129+
let [teams, users] = await Promise.all([this.owner_team, this.owner_user]);
130+
return [...(teams ?? []), ...(users ?? [])];
131+
});
132+
133+
loadVersionsTask = task(async () => {
134+
return (await this.versions) ?? [];
135+
});
103136
}
104137

105138
function compareVersionBySemver(a, b) {

app/routes/crate.js

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,7 @@
11
import { NotFoundError } from '@ember-data/adapter/error';
22
import Route from '@ember/routing/route';
33
import { inject as service } from '@ember/service';
4+
import { waitForPromise } from '@ember/test-waiters';
45

56
export default class CrateRoute extends Route {
67
@service headData;
@@ -26,6 +27,9 @@ export default class CrateRoute extends Route {
2627
setupController(controller, model) {
2728
super.setupController(...arguments);
2829
this.headData.crate = model;
30+
waitForPromise(model.loadOwnerUserTask.perform()).catch(() => {
31+
// ignore all errors if the request fails
32+
});
2933
}
3034

3135
resetController() {

app/routes/crate/version.js

Lines changed: 8 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -51,8 +51,16 @@ export default class VersionRoute extends Route {
5151
waitForPromise(controller.loadReadmeTask.perform()).catch(() => {
5252
// ignored
5353
});
54+
waitForPromise(controller.loadDownloadsTask.perform()).catch(() => {
55+
// ignored
56+
});
5457

5558
let { crate, version } = model;
59+
60+
waitForPromise(crate.loadOwnersTask.perform()).catch(() => {
61+
// ignored
62+
});
63+
5664
if (!crate.documentation || crate.documentation.startsWith('https://docs.rs/')) {
5765
version.loadDocsStatusTask.perform().catch(error => {
5866
// report unexpected errors to Sentry and ignore `ajax()` errors

app/routes/crate/versions.js

Lines changed: 12 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,12 @@
1+
import Route from '@ember/routing/route';
2+
import { waitForPromise } from '@ember/test-waiters';
3+
4+
export default class VersionsRoute extends Route {
5+
setupController(controller) {
6+
super.setupController(...arguments);
7+
let crate = this.modelFor('crate');
8+
controller.set('crate', crate);
9+
// TODO: Add error handling
10+
waitForPromise(crate.loadVersionsTask.perform());
11+
}
12+
}

tests/components/crate-sidebar/playground-button-test.js

Lines changed: 8 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -33,7 +33,8 @@ module('Component | CrateSidebar | Playground Button', function (hooks) {
3333

3434
let store = this.owner.lookup('service:store');
3535
this.crate = await store.findRecord('crate', crate.name);
36-
this.version = (await this.crate.versions).firstObject;
36+
this.version = (await this.crate.versions).slice()[0];
37+
await this.crate.loadOwnersTask.perform();
3738

3839
await render(hbs`<CrateSidebar @crate={{this.crate}} @version={{this.version}} />`);
3940
assert.dom('[data-test-playground-button]').doesNotExist();
@@ -45,7 +46,8 @@ module('Component | CrateSidebar | Playground Button', function (hooks) {
4546

4647
let store = this.owner.lookup('service:store');
4748
this.crate = await store.findRecord('crate', crate.name);
48-
this.version = (await this.crate.versions).firstObject;
49+
this.version = (await this.crate.versions).slice()[0];
50+
await this.crate.loadOwnersTask.perform();
4951

5052
let expectedHref =
5153
'https://play.rust-lang.org/?edition=2021&code=use%20aho_corasick%3B%0A%0Afn%20main()%20%7B%0A%20%20%20%20%2F%2F%20try%20using%20the%20%60aho_corasick%60%20crate%20here%0A%7D';
@@ -63,7 +65,8 @@ module('Component | CrateSidebar | Playground Button', function (hooks) {
6365

6466
let store = this.owner.lookup('service:store');
6567
this.crate = await store.findRecord('crate', crate.name);
66-
this.version = (await this.crate.versions).firstObject;
68+
this.version = (await this.crate.versions).slice()[0];
69+
await this.crate.loadOwnersTask.perform();
6770

6871
render(hbs`<CrateSidebar @crate={{this.crate}} @version={{this.version}} />`);
6972
await waitFor('[data-test-owners]');
@@ -81,7 +84,8 @@ module('Component | CrateSidebar | Playground Button', function (hooks) {
8184

8285
let store = this.owner.lookup('service:store');
8386
this.crate = await store.findRecord('crate', crate.name);
84-
this.version = (await this.crate.versions).firstObject;
87+
this.version = (await this.crate.versions).slice()[0];
88+
await this.crate.loadOwnersTask.perform();
8589

8690
await render(hbs`<CrateSidebar @crate={{this.crate}} @version={{this.version}} />`);
8791
assert.dom('[data-test-playground-button]').doesNotExist();

0 commit comments

Comments
 (0)