Upgrade to Pro
— share decks privately, control downloads, hide ads and more …
Speaker Deck
Sign up for free
Menu
Search
Features
All features
Private URLs
Password Protection
Custom URLS
Scheduled publishing
Remove Branding
Restrict embedding
Deck Collections
Notes
Features
All features
Private URLs
Password Protection
Custom URLS
Scheduled publishing
Remove Branding
Restrict embedding
Deck Collections
Notes
Explore
Featured decks
Featured speakers
Programming
Technology
Storyboards
Explore
Featured decks
Featured speakers
Programming
Technology
Storyboards
Pricing
Search
Sign in
Sign up for free
20241128_NEWT‐Tech-Talk_nakano
Search
reiwa-travel
November 29, 2024
320
0
Share
Embed
Copy iframe code
Copy JS code
Copy link
Start on current slide
20241128_NEWT‐Tech-Talk_nakano
reiwa-travel
November 29, 2024
More Decks by reiwa-travel
See All by reiwa-travel
reiwatravel ai era
reiwatravel_0405
0
910
skill-creator-guide
reiwatravel_0405
0
130
GopherCon-Tour-2025_minami-okada.pdf
reiwatravel_0405
0
430
創業期の急成長を実現した技術戦略を振り返る
reiwatravel_0405
0
230
QA Career Talk vol.5 〜QAエンジニアの生存戦略~
reiwatravel_0405
0
420
20250527_NEWT‐Tech-Talk_semba
reiwatravel_0405
0
550
20250527_NEWT‐Tech-Talk_hosoi
reiwatravel_0405
0
490
20250527_NEWT‐Tech-Talk_fukuda
reiwatravel_0405
0
540
20250527_NEWT‐Tech-Talk_magara
reiwatravel_0405
0
640
Featured
See All Featured
Designing Powerful Visuals for Engaging Learning
tmiket
1
550
VelocityConf: Rendering Performance Case Studies
addyosmani
331
25k
Become a Pro
speakerdeck
PRO
31
6.3k
The World Runs on Bad Software
bkeepers
PRO
72
12k
Utilizing Notion as your number one productivity tool
mfonobong
4
590
Six Lessons from altMBA
skipperchong
29
4.5k
Fight the Zombie Pattern Library - RWD Summit 2016
marcelosomers
234
18k
Designing Dashboards & Data Visualisations in Web Apps
destraynor
232
55k
Dominate Local Search Results - an insider guide to GBP, reviews, and Local SEO
greggifford
PRO
0
330
16th Malabo Montpellier Forum Presentation
akademiya2063
PRO
0
380
Let's Do A Bunch of Simple Stuff to Make Websites Faster
chriscoyier
508
140k
AI in Enterprises - Java and Open Source to the Rescue
ivargrimstad
0
1.5k
Transcript
CONFIDENTIAL NEWT Tech Talk TypeScript Compiler APIを利⽤した データベースドキュメントの⾃動⽣成 Backend Engineer
中野 紘典
CONFIDENTIAL © 2023 Reiwa Travel, Inc. 2 Backend Engineer 中野
紘典 ⾃⼰紹介 Background 2021年にヤフー株式会社(現LINEヤフー株式会社)に新卒⼊社。 社内オブジェクトストレージの開発/運⽤業務を担当。 2024年1⽉より令和トラベルにバックエンドエンジニアとして⼊社。 海外旅⾏アプリ「NEWT」のAPI開発と社内の業務⾃動化基盤の開発 に従事。 Tech • TypeScript(令和トラベルに転職〜) • Go(前職で使ってました) Like • バスケ🏀 • サウナ🧖 • 旅⾏✈
CONFIDENTIAL © 2023 Reiwa Travel, Inc. Agenda 3 • 今までのDBドキュメントの運⽤⽅法と課題
• 今回導⼊したDBドキュメント⾃動⽣成 • どのように移⾏したか • 導⼊した結果と今後
CONFIDENTIAL © 2023 Reiwa Travel, Inc. 今までのDBドキュメント の運⽤⽅法と課題
CONFIDENTIAL © 2023 Reiwa Travel, Inc. DBドキュメントがなぜ令和トラベルで必要なのか? 5 DBをエンジニア以外の社内の様々な関係者が利⽤するから 例)
マーケティングチームの分析メンバーが予約状況可視化のダッシュボード作成 DBのテーブル定義やテーブルの関係をエンジニア以外も理解できる必要がある ツアーの⽬的地集計したいけど ⽬的地のカラムどれだ。。。 😇
CONFIDENTIAL © 2023 Reiwa Travel, Inc. Schema Spyを使⽤してDB情報を可視化 6 Schema
Spyとは? DBからエンティティ関係図を含む HTML ドキュメントを⽣成するツール エンティティ関係図 カラムの情報 SchemaSpyを使⽤してエンジニア以外のメンバーにもDBの情報を公開 → エンジニア以外のメンバーもテーブル定義やテーブルの関係を理解可能
CONFIDENTIAL © 2023 Reiwa Travel, Inc. エンジニア DBのドキュメントを反映する負担が増加 😇 7
エンジニア以外のメンバー ドキュメントあるのでDBを理解しやすい👏 エンジニアから⾒たら課題が。。。
CONFIDENTIAL © 2023 Reiwa Travel, Inc. SchemaSpyへのドキュメントの反映⽅法 8 1. 説明を記載したマークダウンファイル(mdファイル)を記述
2. mdファイルからXMLファイルに変換し、SchmaSpyへ反映するScriptを実行 (SchemaSpyのメタ情報の記載に則したXMLファイルを記載する必要がある) # sample サンプルの説明 ## id idの説明 ## column1 column1の説明 ドキュメント(md) <schemaMeta xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="http://schemaspy.org/xsd/6/schemame ta.xsd"> <tables> <table name="sample" comment="sampleの説明"> <column name="id"comment= "idの説明"/> <column name="column1" comment= "column1の説明"/> </table> </tables> </schemaMeta> SchemaSpyのメタ情報の記載に則したXMLファイル
CONFIDENTIAL © 2023 Reiwa Travel, Inc. 従来の⽅法の課題 9 ソースコードとテーブル定義ドキュメントが別ファイルとして管理 import
{BaseEntity, Column, Entity, PrimaryGeneratedColumn} from "typeorm"; @Entity() export class Sample extends BaseEntity { @PrimaryGeneratedColumn() id: number; @Column() column1: number; } ソースコード # sample サンプルの説明 ## id idの説明 ## column1 column1の説明 ドキュメント(md)
CONFIDENTIAL © 2023 Reiwa Travel, Inc. 従来の⽅法の課題 10 レビューお願いします テーブル定義のmd記載してください
👍 すいません、記載します🙏 ドキュメント(md)がソースコードと離れていることからドキュメントを作成し忘れる 👉 レビューの⼯数が増える 👉 そもそもレビュワーも気づかずドキュメントが作成されないケースも... レビュワー
CONFIDENTIAL © 2023 Reiwa Travel, Inc. 課題を解決するために必要なこと 11 1. コメントとソースファイルを⼀箇所にまとめる🔥
→ コメントを書きやすい状態にすることでエンジニアの負荷を減らす 2. エンジニアにコメントを追加することのメリットを作る🔥 → エンジニアがコメントにメリットを感じればコメントを書くはず
CONFIDENTIAL © 2023 Reiwa Travel, Inc. 今回導⼊した DBドキュメント⾃動⽣成
CONFIDENTIAL © 2023 Reiwa Travel, Inc. 今回導⼊した⽅法 👉ソースファイルにJSDoc でコメントを記載 13
👉TypeScript Compiler APIを 使っ てソースファイルから JSDocを抽出し、XMLファイルを 作成 今まで これから マークダウンでコメント 定義のファイルを作成 マークダウンファイルから XMLファイルを作成 コメントの記載方法 SchemaSpyへの反映⽅法
CONFIDENTIAL © 2023 Reiwa Travel, Inc. JSDocとは? 14 /** *
Represents a book. */ function Book(title) { } • ドキュメント化されるコードの直前に配置 • /** で始める JSのソースコードに注釈を追加するために使われるマークアップ⾔語 JSDocのルール
CONFIDENTIAL © 2023 Reiwa Travel, Inc. JSDocを導⼊した背景 JSDocでコメントを記載することでエディター上でホバー形式で出⼒ 15 コメントを書くことでエンジニアがソースコード上で参照できる→
エンジ ニア側もコメントを書くことにメリットが生まれる
CONFIDENTIAL © 2023 Reiwa Travel, Inc. TypeScript Compiler APIとは? TSのコードをプログラムで解析‧操作できるようにするためのAPI
ソースコードを変換したASTを元に解析処理が可能 let message = "Hello"; console.log(message); ソースコード SyntaxList: let message = "Hello";console.log(message); FirstStatement: let message = "Hello"; VariableDeclarationList: let message = "Hello" LetKeyword: let SyntaxList: message = "Hello" VariableDeclaration: message = "Hello" Identifier: message FirstAssignment: = StringLiteral: "Hello" SemicolonToken: ; ExpressionStatement: console.log(message); CallExpression: console.log(message) PropertyAccessExpression: console.log Identifier: console DotToken: . Identifier: log OpenParenToken: ( SyntaxList: message Identifier: message CloseParenToken: ) SemicolonToken: ; EndOfFileToken: AST 変換 16
CONFIDENTIAL © 2023 Reiwa Travel, Inc. TypeScript Compiler APIを使⽤した背景 ソースファイルを解析してJSDocを抽出するコードをTypeScript
Compiler APIなら簡単に実装可能 JSDocだけでなく@Entityなどの情報もAPIを通して取得できるので ソースファイルの特定も容易にできた 17 import {BaseEntity, Column, Entity, PrimaryGeneratedColumn} from "typeorm"; /** * サンプルエンティティの説明 */ @Entity() export class Sample extends BaseEntity { @PrimaryGeneratedColumn() id: number; @Column() column1: number; } 変換 SyntaxList: …. ImportDeclaration: ClassDeclaration: … JSDocComment: /** * サンプルエンティティの説明 */ ….
CONFIDENTIAL © 2023 Reiwa Travel, Inc. どのように移⾏したか
CONFIDENTIAL © 2023 Reiwa Travel, Inc. 移⾏前〜 ⽣成AIで軽く試す 19 TypeScript
Compiler API は知見が全くなかったので 簡単なJSDocを記載したサンプルで生成AIを使って試してみた 👉TypeScript Compiler APIの使い方と簡単に実現できるか調べるため TypeScript Compiler API を使えば、以下が簡単に実装できると分かった💪 1. @Entityデコレータの検出 👉 ソースファイルの特定が可能だから 2. JSDocを検出&値を取得すること 👉 ソースファイルからコメントを抽出することが可能だから
CONFIDENTIAL © 2023 Reiwa Travel, Inc. どのように移⾏するか 20 フェーズ1 mdファイルから該当するソー
スファイルにJSDoc コメントを転記する フェーズ2 JSDocからSchemaSpyの メタデータの形式に則した XMLファイルを作成する
CONFIDENTIAL © 2023 Reiwa Travel, Inc. どのように移⾏するか 21 フェーズ1 マークダウンのドキュメン
トファイルから該当する ソースファイルにJSDoc コメントを転記する フェーズ2 JSDocからSchemaSpyの メタデータの形式に則した XMLファイルを作成する
CONFIDENTIAL © 2023 Reiwa Travel, Inc. マークダウンファイルからJSDocへの変換 - 全体図 22
JSDocコメントの⽣成 TypeScriptファイルへJSDocを適⽤ mdファイルの検出 とパース
CONFIDENTIAL © 2023 Reiwa Travel, Inc. マークダウンファイルからJSDocへの変換 - マークダウンファイルの検出とパース処理 23
# sample サンプルの説明 ## id idの説明 ## column1 column1の説明 mdファイル 各⾏は特定のパターンに基づいて処理 • # で始まる⾏はテーブル定義として認識され、直後の⾏はそのテーブルの説明⽂として保存 • ## で始まる⾏はカラム定義として認識同様に、直後の⾏はそのカラムの説明⽂として保存
CONFIDENTIAL © 2023 Reiwa Travel, Inc. マークダウンファイルからJSDocへの変換 - JSDocコメントの⽣成 24
{ title: "sample", content: ["サンプルの説明"], subSections: [ { title: "id", content: ["idの説明"] }, { title: "column1", content: ["column1の説明"] } ] } { // テーブル用のJSDoc classJSDoc: "/**\n * サンプルの説明\n */", // カラム用のJSDoc columnJSDocs: { id: "/**\n * idの説明\n */", column1: "/**\n * column1の説明\n */" } } mdのパース処理で作成した中間データをJSDocコメントに変換 • メインセクションの説明⽂をテーブルの説明としてJSDocコメントに変換 • サブセクションの説明⽂を各カラムの説明として形式のJSDocコメントに変換し、キー名と紐付け mdのパース処理で作成した中間データ JSDocに変換した中間データ
CONFIDENTIAL © 2023 Reiwa Travel, Inc. マークダウンファイルからJSDocへの変換 - TypeScriptファイルへJSDocを適⽤ 25
/** * サンプルの説明 */ @Entity() export class Sample extends BaseEntity { /** * idの説明 */ @PrimaryGeneratedColumn() id: number; /** * column1の説明 */ @Column() column1: number; TypeScript Compiler APIを使⽤し以下ロジックでJSDocをソースファイルに追加 • @Entityがあるクラスの場合 その上にテーブルの説明を追加 • @PrimaryGeneratedColumn、@Columnの場合、カラムの説明を追加
CONFIDENTIAL © 2023 Reiwa Travel, Inc. どのように移⾏するか 26 フェーズ1 マークダウンのドキュメント
ファイルから該当するEnソー スファイルにJSDoc コメントを転記する フェーズ2 JSDocからSchemaSpyの メタデータの形式に則した XMLファイルを作成する
CONFIDENTIAL © 2023 Reiwa Travel, Inc. JSDocからSchemaSpyのXMLファイル変換 - 全体図 27
ファイル検索 エンティティ解析 ドキュメント⽣成
CONFIDENTIAL © 2023 Reiwa Travel, Inc. JSDocからSchemaSpyのXMLファイル変換 - ファイル検索 28
DB名に基づいて解析対象のTSファイルを特定 • コマンドライン引数からDB名を取得し、そのDBに対応するモジュールディレクトリを決定 // 対象ファイルリスト const entityFiles = [ "src/modules/sample1/sample1. entity.ts", "src/modules/sample2/sample2. entity.ts" ]
CONFIDENTIAL © 2023 Reiwa Travel, Inc. JSDocからSchemaSpyのXMLファイル変換 - エンティティ解析 29
/** * sampleの説明 */ @Entity() export class Sample extends BaseEntity { /** * idの説明 */ @PrimaryGeneratedColumn() id: number; /** * column1の説明 */ @Column() column1: number; // EntityInfo構造体 const entityInfo = { name: "sample", description: "sampleの説明", properties: [ { name: "id", type: "number", description: "idの説明" }, { name: "column1", type: "number", description: "column1の説明" } ] } 解析するtsファイル 解析後作成された中間データ
CONFIDENTIAL © 2023 Reiwa Travel, Inc. JSDocからSchemaSpyのXMLファイル変換 - ドキュメント⽣成 30
// EntityInfo構造体 const entityInfo = { name: "sample", description: "sampleの説明", properties: [ { name: "id", type: "number", description: "idの説明" }, { name: "column1", type: "number", description: "column1の説明" } ] } <schemaMeta xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="http://schemaspy.org/xsd/6/schemame ta.xsd"> <tables> <table name="sample" comment="サンプルの説明"> <column name="id"comment= "idの説明"/> <column name="column1" comment= "column1の説明"/> </table> </tables> </schemaMeta> XMLファイル 抽出したエンティティ情報をSchemaSpy形式のXMLファイルに変換 SchemaSpy互換のXMLファイルとして出⼒することで、DBドキュメントが⾃動⽣成
CONFIDENTIAL © 2023 Reiwa Travel, Inc. 導⼊した結果と今後
CONFIDENTIAL © 2023 Reiwa Travel, Inc. 導⼊した結果 32 mdファイル(全64ファイル)に記載されていたテーブル定義を全てJSDocのコメントに変換できた🎉 •
JSDocでコメントをつけたことでホバー機能で詳細を確認可能 👉 ソースファイルとコメントが一箇所になった 👉 JSDocがつくことでエンジニアにもコメントを書くメリットが生まれた
CONFIDENTIAL © 2023 Reiwa Travel, Inc. @Field(() => Boolean, {
description: `column1の説明`, }) /** column1の説明 */ @Column({ type: "boolean", default: false }) column1: boolean; 苦労した点 33 コメント追加が意図しない箇所にされてしまう 本来は@Fieldの上に配置したい。。。😇 現在チームで規定されている型と異なるパターンが存在 例)@Columnデコレータの上に別のデコレータ ソースファイルの書き方が統一されている 👉解析処理の観点でも大事 問題点 原因
CONFIDENTIAL © 2023 Reiwa Travel, Inc. 今後の課題 34 マークダウンのコメント定義にないテーブル、またはカラムはいまだに JSDocもなく、SchemaSpyのコメントとしても反映できていない
• GithubActionsでPR時にEntityファイルにJSDocの記載があるか チェックする機能を導⼊ • モジュールごとにコメントの記載率を可視化 ⽬指せ、JSDoc記載率100%🔥
CONFIDENTIAL © 2023 Reiwa Travel, Inc. 今回の学びと今後の展望 35 今回の実装でTypeScript Compiler
APIを使用すれば、ts ファイルを解析処理が容易にできることがわかった ライブラリの変更やアップデートで多くファイルの表記を変更す る場合などに応用できそうなのでやってみたい🔥 今回の学び 今後の展望
CONFIDENTIAL © 2023 Reiwa Travel, Inc. まとめ 36 SchemaSpyを使⽤してエンジニア以外のメンバーにもDBの情報を公開していた ソースコードとテーブル定義ドキュメントが別ファイルとして管理しているため、
反映作業がエンジニアの負担になっていた • コメント定義⽤のmdファイルを作成 →ソースファイルにJSDocでコメントを追加 • ソースファイルをTypeScript Compiler APIで解析し、XMLファイルを作成 ソースファイルにJSDocでコメントを書けるようになることで エンジニアがコメントを反映する負担が減るだけでなく、書くメリットが⽣まれた 問題 実装 結果
Thank you! CONFIDENTIAL © 2023 Reiwa Travel, Inc.