Skip to content

Commit ca79829

Browse files
committed
Add custom avatar
1 parent 8f9186f commit ca79829

4 files changed

Lines changed: 42 additions & 5 deletions

File tree

package.json

Lines changed: 4 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -4033,6 +4033,10 @@
40334033
"fileRange": {
40344034
"type": "string",
40354035
"markdownDescription": "Specifies the format of a range in a file URL for the custom remote service\n\nAvailable tokens\\\n`${start}` — starting line\\\n`${end}` — ending line"
4036+
},
4037+
"avatar": {
4038+
"type": "string",
4039+
"markdownDescription": "Specifies the format of a avatar url for the custom remote service\n\nAvailable tokens\\\n`${email}` — contributor email\\\n`${name}` — email local-part\\\n`${domain}` — email domain\\\n`${size}` — avatar size"
40364040
}
40374041
},
40384042
"additionalProperties": false

src/avatars.ts

Lines changed: 24 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -5,6 +5,7 @@ import type { GravatarDefaultStyle } from './config';
55
import type { StoredAvatar } from './constants.storage';
66
import { Container } from './container';
77
import type { CommitAuthor } from './git/models/author';
8+
import { CustomRemote } from './git/remotes/custom';
89
import { getGitHubNoReplyAddressParts } from './git/remotes/github';
910
import { configuration } from './system/-webview/configuration';
1011
import { getContext } from './system/-webview/context';
@@ -130,7 +131,7 @@ function getAvatarUriCore(
130131
if (
131132
!options?.cached &&
132133
repoPathOrCommit != null &&
133-
getContext('gitlens:repos:withHostingIntegrationsConnected')?.includes(
134+
getContext('gitlens:repos:withRemotes')?.includes(
134135
typeof repoPathOrCommit === 'string' ? repoPathOrCommit : repoPathOrCommit.repoPath,
135136
)
136137
) {
@@ -228,16 +229,34 @@ async function getAvatarUriFromRemoteProvider(
228229
// account = await remote?.provider.getAccountForEmail(email, { avatarSize: size });
229230
// } else {
230231
if (typeof repoPathOrCommit !== 'string') {
231-
const remote = await Container.instance.git
232+
const remoteWithIntegration = await Container.instance.git
232233
.getRepositoryService(repoPathOrCommit.repoPath)
233234
.remotes.getBestRemoteWithIntegration();
234-
if (remote?.supportsIntegration()) {
235+
236+
if (remoteWithIntegration?.supportsIntegration()) {
235237
account = await (
236-
await remote.getIntegration()
237-
)?.getAccountForCommit(remote.provider.repoDesc, repoPathOrCommit.ref, {
238+
await remoteWithIntegration.getIntegration()
239+
)?.getAccountForCommit(remoteWithIntegration.provider.repoDesc, repoPathOrCommit.ref, {
238240
avatarSize: size,
239241
});
240242
}
243+
244+
if (!account) {
245+
const remoteWithProvider = await Container.instance.git
246+
.getRepositoryService(repoPathOrCommit.repoPath)
247+
.remotes.getBestRemoteWithProvider();
248+
249+
if (remoteWithProvider?.provider instanceof CustomRemote) {
250+
const avatarUrl = remoteWithProvider.provider.getUrlForAvatar(email, size);
251+
if (avatarUrl != null) {
252+
avatar.uri = Uri.parse(avatarUrl);
253+
avatar.timestamp = Date.now();
254+
avatar.retries = 0;
255+
avatarCache.set(`${md5(email.trim().toLowerCase())}:${size}`, { ...avatar });
256+
return avatar.uri;
257+
}
258+
}
259+
}
241260
}
242261

243262
if (account?.avatarUrl == null) {

src/config.ts

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -695,6 +695,7 @@ export interface RemotesUrlsConfig {
695695
readonly fileInCommit: string;
696696
readonly fileLine: string;
697697
readonly fileRange: string;
698+
readonly avatar?: string;
698699
}
699700

700701
interface StatusBarConfig {

src/git/remotes/custom.ts

Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -41,6 +41,19 @@ export class CustomRemote extends RemoteProvider {
4141
return Promise.resolve(undefined);
4242
}
4343

44+
getUrlForAvatar(email: string, size: number): string | undefined {
45+
if (this.urls.avatar != null) {
46+
const [name, domain] = email.split('@');
47+
return this.encodeUrl(
48+
interpolate(
49+
this.urls.avatar,
50+
this.getContext({ name: name, domain: domain, email: email, size: String(size) }),
51+
),
52+
);
53+
}
54+
return undefined;
55+
}
56+
4457
protected override getUrlForRepository(): string {
4558
return this.getUrl(this.urls.repository, this.getContext());
4659
}

0 commit comments

Comments
 (0)