Notion AI でコミットメッセージを生成する実験
以前にも少し書いたように、AI が diff からコミットメッセージを生成してくれるとうれしい。
しばらく Notion AI を使ってみて、「わりといけそうかな」という気もしてきたので試してみた。
準備
他の AI チャットなどは使ったことがないので「そういうもの」なのかは不明だけど、Notion AI では「AI に依頼」を実行すると前後のテキストなどに影響されるように見える。
よって、最初に下記のようなメモを作成する。
diff からコミットメッセージを生成する
現在は手動でコミットメッセージを入力している
そのときは、下記のような情報も付与している。
Conventional Commits
コミットメッセージのテンプレート
type: Subject
# feat: (new feature for the user, not a new feature for build script)
# fix: (bug fix for the user, not a fix to a build script)
# deps: dependencies
# docs: (changes to the documentation)
# style: (formatting, missing semi colons, etc; no production code change)
# refactor: (refactoring production code, eg. renaming a variable)
# test: (adding missing tests, refactoring tests; no production code change)
# chore: (updating grunt tasks etc; no production code change)
#
# ## minor change
#
# Format: `<type>(<scope>): <subject>`
#
# `<scope>` is optional
#
# ## major(breaking) change
#
# Format: `<type>(<scope>)!: <subject>`
#
# `<scope>` is optional
#
# ## Example
#
# ```
# feat: add hat wobble
# ^--^ ^------------^
# | |
# | +-> Summary in present tense.
# |
# +-------> Type: chore, docs, feat, fix, refactor, style, or test.
# ```
#
# ## References:
#
# - https://gist.github.com/joshbuchea/6f47e86d2510bce28f8e7f42ae84c716
# - https://zenn.dev/uochan/articles/2021-12-08-vim-conventional-commits
# - https://www.conventionalcommits.org/ja/v1.0.0/
# - https://www.conventionalcommits.org/
# - https://seesparkbox.com/foundry/semantic_commit_messages
# - http://karma-runner.github.io/1.0/dev/git-commit-msg.html
# ==== The Seven Rules ====
# 1. Separate subject from body with a blank line
# 2. Limit the subject line to 50 characters
# 3. Capitalize the subject line
# 4. Do not end the subject line with a period
# 5. Use the imperative mood in the subject line
# 6. Wrap the body at 72 characters
# 7. Use the body to explain what and why vs. how
#
# How to Write a Git Commit Message http://chris.beams.io/posts/git-commit/
# for http://memo.goodpatch.co/2016/07/beautiful-commits-with-emojis/
上記メモに下記を追加する。
diff は下記の内容を貼り付けてある。
上記をふまえて diff からコミットメッセージを生成してみる
diff --git a/src/lib/reqid.ts b/src/lib/reqid.ts
index f26faff..4380d78 100644
--- a/src/lib/reqid.ts
+++ b/src/lib/reqid.ts
@@ -70,6 +70,7 @@ export async function dec(
export type ReqInfo = {
/**
* The id of subscription that is used to receive response from user.
+ * it has prefix with `req-`
*/
sunbscription: string
/**
@@ -105,7 +106,7 @@ export type MakeReqInfoParams = {
* @returns the information data.
*/
export async function getReqId(params: MakeReqInfoParams): Promise<ReqInfo> {
- const sunbscription = randomUUID()
+ const sunbscription = `req-${randomUUID()}`
const filter = createHash('sha256')
.update(sunbscription, 'utf8')
.digest('hex')
diff --git a/test/index.integration.http.spec.ts b/test/index.integration.http.spec.ts
index 5e2dccd..7e6038a 100644
--- a/test/index.integration.http.spec.ts
+++ b/test/index.integration.http.spec.ts
@@ -12,7 +12,7 @@ import type { getReqId } from '../src/lib/reqid.js'
// topics
const topid = 'test-integration-topic-id'
// subscriptions
-const sunbscription = 'test-subscription'
+const sunbscription = 'req-test-subscription'
const filter = 'test-fileter'
const handleId = 'test-handleid'
diff --git a/test/index.unit.http.spec.ts b/test/index.unit.http.spec.ts
index d2be91e..8209fbd 100644
--- a/test/index.unit.http.spec.ts
+++ b/test/index.unit.http.spec.ts
@@ -17,7 +17,7 @@ import type { getReqId } from '../src/lib/reqid.js'
// topics
const topid = 'test-unit-topic-id'
// subscriptions
-const sunbscription = 'test-subscription'
+const sunbscription = 'req-test-subscription'
const filter = 'test-fileter'
const handleId = 'test-handleid'
diff --git a/test/lib/reqid.spec.ts b/test/lib/reqid.spec.ts
index 54e3b6a..7454794 100644
--- a/test/lib/reqid.spec.ts
+++ b/test/lib/reqid.spec.ts
@@ -96,9 +96,9 @@ describe('getReqId', () => {
const { mockCreateCipheriv } = (mockCrypto as any)._getMocks()
const i = await getReqId({ password, salt, sheetId: '', bundleId: '' })
- expect(i.sunbscription).toEqual('50a11b0b-fea7-47b3-9934-b2191b5b6b29') // randomUUID を固定してあるので、常に同じ値.
+ expect(i.sunbscription).toEqual('req-50a11b0b-fea7-47b3-9934-b2191b5b6b29') // randomUUID を固定してあるので、常に同じ値.
expect(i.filter).toEqual(
- 'cb6964b653b386c11b6a2b2c160e4d6442b21c8865b1f7f05d6f4f7cd03d752c'
+ '00fc2b4541cfc9128161c10a88d1bda33f0fa90416dfbac1e357e170ed68e90b'
) // randomUUID を固定してあるので、常に同じ値.
// handleId はメソッドをコールしていたら暗号化されているだろう、ということにする.
上記のコードブロックを選択し ctrl
+j
で「コミットメッセージを生成してください。」と入力すると下記のように生成された。
feat: update reqid.ts
Add prefix req-
to sunbscription
on getReqId
function to identify it.
Details
-
sunbscription
is a subscription id that is used to receive response from user. Add prefixreq-
to it to identify it as a request subscription. - Update
getReqId
function to add prefixreq-
tosunbscription
. - Update
test/index.integration.http.spec.ts
,test/index.unit.http.spec.ts
, andtest/lib/reqid.spec.ts
to usereq-test-subscription
as subscription name.
生成されたメッセージは良いようなそうでもないような感じだけど、手順的には「切り貼りするのはめんどう」だった。
次からは diff のコピペだけになるからもう少し楽だけど、実際に使ってみるかはちょっと悩ましいところ(すなおにそれ用の拡張機能を探せという話でもある)。
別の diff で試してみた。
上で試したメモに見出しと diff のコードブロックを追加して AI の「続きを書く」を実行。
別のコミットのメッセージを生成
diff --git a/package.json b/package.json
index 8b28e39..cf804d6 100644
--- a/package.json
+++ b/package.json
@@ -16,7 +16,9 @@
},
"scripts": {
"start": "npm run build && node dist/main.js",
+ "debug": "npm run build:debug && node --inspect dist/main.js",
"build": "npm run clean && tsc && rimraf dist/test && mv dist/src/* dist/ && rimraf dist/src",
+ "build:debug": "npm run clean && tsc --sourceMap --sourceRoot \"${PWD}\" && rimraf dist/test && mv dist/src/* dist/ && rimraf dist/src",
"test": "node --experimental-vm-modules node_modules/.bin/jest",
"lint:type-check": "tsc --noEmit",
"clean": "rimraf \"dist/\"",
生成されたコミットメッセージ。
chore: add debug script
Add debug
script to package.json
to start node with inspect option and build:debug
script to compile with source map.
type を使い分けてくれたのはちょっと意外だった(正直なところ今回も feat
にされるかと予想していた)。
ということで参考にさせていただいた。
いまのメモに「よいコミットメッセージとは」的な記事の引用などを貼り付けておいて、その下に diff を貼り付けたら、さらに良くなりそうな気がしないでもない、かな。
さらに別のコミットメッセージを生成しようとしたのだが
下記の diff だとファイル別の変更点が列挙されるだけだった。変更箇所が多すぎるという気もするので、AI がそれっぽくないメッセージを生成したら、変更の仕方が悪いという風に考えるのもありかもしれない。
長いので折りたたみます
diff --git a/src/lib/notion.ts b/src/lib/notion.ts
index 63a18cd..a053018 100644
--- a/src/lib/notion.ts
+++ b/src/lib/notion.ts
@@ -29,9 +29,25 @@ export function pageParams(repo: RepoItem): {
}
]
},
+ name: {
+ rich_text: [
+ {
+ type: 'text',
+ text: { content: repo.name }
+ }
+ ]
+ },
title: {
title: [{ type: 'text', text: { content: repo.nameWithOwner } }]
},
+ owner: {
+ rich_text: [
+ {
+ type: 'text',
+ text: { content: repo.owner.login }
+ }
+ ]
+ },
//openGraphImageUrl: {
// files: [
// {
@@ -46,6 +62,9 @@ export function pageParams(repo: RepoItem): {
repositoryTopics: {
multi_select: (repo.repositoryTopics || []).map(({ name }) => ({ name }))
},
+ pushedAt: {
+ date: { start: repo.pushedAt }
+ },
updatedAt: {
date: { start: repo.updatedAt }
},
@@ -61,7 +80,7 @@ export async function send(client: Client, databaseId: string, repo: RepoItem) {
.query({
database_id: databaseId,
filter: {
- property: 'name',
+ property: 'title',
title: {
equals: repo.nameWithOwner
}
diff --git a/src/lib/repo.ts b/src/lib/repo.ts
index 4c51851..129bd3b 100644
--- a/src/lib/repo.ts
+++ b/src/lib/repo.ts
@@ -2,7 +2,10 @@ export type RepoItem = {
createdAt: string
description: string
nameWithOwner: string
+ name: string
openGraphImageUrl: string
+ owner: { login: string; id?: string }
+ pushedAt: string
repositoryTopics: Record<'name', string>[] | null
updatedAt: string
url: string
diff --git a/src/lib/validate.ts b/src/lib/validate.ts
index 679cb20..6cf5f70 100644
--- a/src/lib/validate.ts
+++ b/src/lib/validate.ts
@@ -10,8 +10,11 @@ export const RepoItemSchema = {
type: 'object',
required: [
'createdAt',
+ 'name',
'nameWithOwner',
'openGraphImageUrl',
+ 'owner',
+ 'pushedAt',
'updatedAt',
'url'
],
@@ -23,6 +26,9 @@ export const RepoItemSchema = {
description: {
type: 'string'
},
+ name: {
+ type: 'string'
+ },
nameWithOwner: {
type: 'string'
},
@@ -30,6 +36,15 @@ export const RepoItemSchema = {
type: 'string',
format: 'uri'
},
+ owner: {
+ type: 'object',
+ required: ['login'],
+ properties: {
+ login: {
+ type: 'string'
+ }
+ }
+ },
repositoryTopics: {
type: ['array', 'null'],
items: {
@@ -42,6 +57,10 @@ export const RepoItemSchema = {
}
}
},
+ pushedAt: {
+ type: 'string',
+ format: 'date-time'
+ },
updatedAt: {
type: 'string',
format: 'date-time'
diff --git a/test/lib/notion.spec.ts b/test/lib/notion.spec.ts
index 721cb30..f70bee3 100644
--- a/test/lib/notion.spec.ts
+++ b/test/lib/notion.spec.ts
@@ -8,9 +8,14 @@ describe('pageParams', () => {
createdAt: '2022-04-11T07:40:07Z',
description:
'Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.',
+ name: 'aaaaa',
nameWithOwner: 'hankei6km/aaaaa',
openGraphImageUrl:
'https://opengraph.githubassets.com/8a871d34480686c2e48e3dd1252aa8239e6564ed851beb3c77f174b138afea4c/hankei6km/gas-feed2notion',
+ owner: {
+ id: 'abc123',
+ login: 'hankei6km'
+ },
repositoryTopics: [
{
name: 'google-apps-script'
@@ -28,6 +33,7 @@ describe('pageParams', () => {
name: 'typescript'
}
],
+ pushedAt: '2023-02-08T08:10:47Z',
updatedAt: '2023-02-08T08:10:47Z',
url: 'https://github.com/hankei6km/aaaaa'
})
@@ -55,9 +61,29 @@ describe('pageParams', () => {
}
]
},
+ name: {
+ rich_text: [
+ {
+ type: 'text',
+ text: {
+ content: 'aaaaa'
+ }
+ }
+ ]
+ },
title: {
title: [{ type: 'text', text: { content: 'hankei6km/aaaaa' } }]
},
+ owner: {
+ rich_text: [
+ {
+ type: 'text',
+ text: {
+ content: 'hankei6km'
+ }
+ }
+ ]
+ },
repositoryTopics: {
multi_select: [
{
@@ -77,6 +103,9 @@ describe('pageParams', () => {
}
]
},
+ pushedAt: {
+ date: { start: '2023-02-08T08:10:47Z' }
+ },
updatedAt: {
date: { start: '2023-02-08T08:10:47Z' }
},
@@ -90,10 +119,16 @@ describe('pageParams', () => {
pageParams({
createdAt: '2022-02-05T14:16:25Z',
description: '',
+ name: 'aaaaa',
nameWithOwner: 'hankei6km/aaaaa',
openGraphImageUrl:
'https://opengraph.githubassets.com/0e9a92dd721c4e6cb2b82df96a66133ac93d43c4233159c1d1c3d1bc420a4fd2/hankei6km/chanpuru',
+ owner: {
+ id: 'abc123',
+ login: 'hankei6km'
+ },
repositoryTopics: null,
+ pushedAt: '2022-02-23T13:55:00Z',
updatedAt: '2022-02-23T13:55:00Z',
url: 'https://github.com/hankei6km/aaaaa'
})
@@ -120,12 +155,35 @@ describe('pageParams', () => {
}
]
},
+ name: {
+ rich_text: [
+ {
+ type: 'text',
+ text: {
+ content: 'aaaaa'
+ }
+ }
+ ]
+ },
title: {
title: [{ type: 'text', text: { content: 'hankei6km/aaaaa' } }]
},
+ owner: {
+ rich_text: [
+ {
+ type: 'text',
+ text: {
+ content: 'hankei6km'
+ }
+ }
+ ]
+ },
repositoryTopics: {
multi_select: []
},
+ pushedAt: {
+ date: { start: '2022-02-23T13:55:00Z' }
+ },
updatedAt: {
date: { start: '2022-02-23T13:55:00Z' }
},
@@ -142,10 +200,16 @@ describe('send', () => {
const repo = {
createdAt: '2022-02-05T14:16:25Z',
description: '',
+ name: 'aaaaa',
nameWithOwner: 'hankei6km/aaaaa',
openGraphImageUrl:
'https://opengraph.githubassets.com/0e9a92dd721c4e6cb2b82df96a66133ac93d43c4233159c1d1c3d1bc420a4fd2/hankei6km/chanpuru',
+ owner: {
+ id: 'abc123',
+ login: 'hankei6km'
+ },
repositoryTopics: null,
+ pushedAt: '2022-02-23T13:55:00Z',
updatedAt: '2022-02-23T13:55:00Z',
url: 'https://github.com/hankei6km/aaaaa'
}
@@ -157,7 +221,7 @@ describe('send', () => {
expect(mockClient.databases.query).toBeCalledWith({
database_id: databaseId,
filter: {
- property: 'name',
+ property: 'title',
title: {
equals: repo.nameWithOwner
}
@@ -178,7 +242,7 @@ describe('send', () => {
expect(mockClient.databases.query).toBeCalledWith({
database_id: databaseId,
filter: {
- property: 'name',
+ property: 'title',
title: {
equals: repo.nameWithOwner
}
diff --git a/test/lib/reposition.spec.ts b/test/lib/reposition.spec.ts
index 693e5c0..f2e116e 100644
--- a/test/lib/reposition.spec.ts
+++ b/test/lib/reposition.spec.ts
@@ -23,19 +23,31 @@ describe('reposition', () => {
JSON.stringify({
createdAt: '2022-02-05T14:16:25Z',
description: '',
+ name: 'aaaaa',
nameWithOwner: 'hankei6km/aaaaa',
openGraphImageUrl:
'https://opengraph.githubassets.com/0e9a92dd721c4e6cb2b82df96a66133ac93d43c4233159c1d1c3d1bc420a4fd2/hankei6km/chanpuru',
+ owner: {
+ id: 'abc123',
+ login: 'hankei6km'
+ },
repositoryTopics: null,
+ pushedAt: '2022-02-23T13:55:00Z',
updatedAt: '2022-02-23T13:55:00Z',
url: 'https://github.com/hankei6km/aaaaa'
}),
JSON.stringify({
createdAt: '2022-02-05T14:16:25Z',
description: '',
+ name: 'aaaaa',
nameWithOwner: 'hankei6km/aaaaa',
openGraphImageUrl:
'https://opengraph.githubassets.com/0e9a92dd721c4e6cb2b82df96a66133ac93d43c4233159c1d1c3d1bc420a4fd2/hankei6km/chanpuru',
+ owner: {
+ id: 'abc123',
+ login: 'hankei6km'
+ },
+ pushedAt: '2022-02-23T13:55:00Z',
repositoryTopics: null,
updatedAt: '2022-02-23T13:55:00Z',
url: 'https://github.com/hankei6km/aaaaa'
@@ -59,11 +71,17 @@ describe('reposition', () => {
JSON.stringify({
createdAt: '2022-02-05T14:16:25Z',
description: '',
+ name: 'aaaaa',
nameWithOwner: 'hankei6km/aaaaa',
+ owner: {
+ id: 'abc123',
+ login: 'hankei6km'
+ },
openGraphImageUrl:
'https://opengraph.githubassets.com/0e9a92dd721c4e6cb2b82df96a66133ac93d43c4233159c1d1c3d1bc420a4fd2/hankei6km/chanpuru',
repositoryTopics: null,
updatedAt: '2022-02-23T13:55:00Z',
+ pushedAt: '2022-02-23T13:55:00Z',
url: 'https://github.com/hankei6km/aaaaa'
}),
JSON.stringify({})
@@ -87,10 +105,16 @@ describe('reposition', () => {
JSON.stringify({
createdAt: '2022-02-05T14:16:25Z',
description: '',
+ name: 'hankei6km/aaaaa',
nameWithOwner: 'hankei6km/aaaaa',
openGraphImageUrl:
'https://opengraph.githubassets.com/0e9a92dd721c4e6cb2b82df96a66133ac93d43c4233159c1d1c3d1bc420a4fd2/hankei6km/chanpuru',
+ owner: {
+ id: 'abc123',
+ login: 'hankei6km'
+ },
repositoryTopics: null,
+ pushedAt: '2022-02-23T13:55:00Z',
updatedAt: '2022-02-23T13:55:00Z',
url: 'https://github.com/hankei6km/aaaaa'
})
diff --git a/test/lib/validate.spec.ts b/test/lib/validate.spec.ts
index b712349..f113554 100644
--- a/test/lib/validate.spec.ts
+++ b/test/lib/validate.spec.ts
@@ -7,9 +7,14 @@ describe('validateRepoItem', () => {
createdAt: '2022-04-11T07:40:07Z',
description:
'Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.',
+ name: 'aaaaa',
nameWithOwner: 'hankei6km/aaaaa',
openGraphImageUrl:
'https://opengraph.githubassets.com/8a871d34480686c2e48e3dd1252aa8239e6564ed851beb3c77f174b138afea4c/hankei6km/gas-feed2notion',
+ owner: {
+ id: 'abc123',
+ login: 'hankei6km'
+ },
repositoryTopics: [
{
name: 'google-apps-script'
@@ -27,6 +32,7 @@ describe('validateRepoItem', () => {
name: 'typescript'
}
],
+ pushedAt: '2023-02-08T08:10:47Z',
updatedAt: '2023-02-08T08:10:47Z',
url: 'https://github.com/hankei6km/aaaaa'
})
@@ -35,10 +41,16 @@ describe('validateRepoItem', () => {
validateRepoItem({
createdAt: '2022-02-05T14:16:25Z',
description: '',
+ name: 'aaaaa',
nameWithOwner: 'hankei6km/aaaaa',
openGraphImageUrl:
'https://opengraph.githubassets.com/0e9a92dd721c4e6cb2b82df96a66133ac93d43c4233159c1d1c3d1bc420a4fd2/hankei6km/chanpuru',
+ owner: {
+ id: 'abc123',
+ login: 'hankei6km'
+ },
repositoryTopics: null,
+ pushedAt: '2022-02-23T13:55:00Z',
updatedAt: '2022-02-23T13:55:00Z',
url: 'https://github.com/hankei6km/aaaaa'
})
@@ -51,12 +63,18 @@ describe('validateRepoItem', () => {
createdAt: 'invalid date',
description:
'Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.',
+ name: 'aaaaa',
nameWithOwner: 'hankei6km/aaaaa',
openGraphImageUrl:
'<https://opengraph.githubassets.com/8a871d34480686c2e48e3dd1252aa8239e6564ed851beb3c77f174b138afea4c/hankei6km/gas-feed2notion>',
+ owner: {
+ id: 'abc123',
+ login: 'hankei6km'
+ },
repositoryTopics: {
name: 'invalid topic'
},
+ pushedAt: '2023-02-08T08:10:47Z',
updatedAt: '2023-02-08T08:10:47Z',
url: 'https://github.com/hankei6km/aaaaa'
})
@@ -66,10 +84,16 @@ describe('validateRepoItem', () => {
createdAt: '2022-04-11T07:40:07Z',
description:
'Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua.',
+ name: 'aaaaa',
nameWithOwner: 'hankei6km/aaaaa',
openGraphImageUrl:
'<https://opengraph.githubassets.com/8a871d34480686c2e48e3dd1252aa8239e6564ed851beb3c77f174b138afea4c/hankei6km/gas-feed2notion>',
+ owner: {
+ id: 'abc123',
+ login: 'hankei6km'
+ },
repositoryTopics: null,
+ pushedAt: '2023-02-08T08:10:47Z',
updatedAt: '2023-02-08T08:10:47Z',
url: '<https://github.com/hankei6km/aaaa>'
})