スマヌトキャンプ株匏䌚瀟のブログ - TECH PLAY

TECH PLAY

スマヌトキャンプ株匏䌚瀟

スマヌトキャンプ株匏䌚瀟 の技術ブログ

å…š226ä»¶

こんにちはスマヌトキャンプ、゚ンゞニアの関口です 私は珟圚BOXILず連携させる新芏アプリケヌションの開発に携わっおおりたす。 このアプリケヌションは、バック゚ンドAPIはGo 、フロント゚ンドはTypeScript/Next.jsで構成されおいたす。 このプロゞェクトの䞭で私は認蚌機胜を担圓したした。認蚌機胜はAuth0ずいうIDaaSを利甚しお実装しおいたす。同じ様な構成で認蚌機胜を実装したいず考えおいる方の理解の助けになればず思い、 このアプリケヌションの構成に寄せる圢でNext.jsずAuth0を連携した認蚌機胜を実装する方法を玹介したす。 Next.jsずは Auth0ずは auth0-reactずは 実装 たずめ Next.jsずは Next.jsずはReactをベヌスずしたWebアプリケヌションフレヌムワヌクです。Next.jsはVercelずいうホスティングサヌビスを提䟛しおいるVercel瀟が提䟛しおいたす。Next.jsはペヌゞ単䜍でHTMLの生成方法をSSRかSSGで遞択できたり、ファむルベヌスのルヌティングを備えおいたす。 公匏サむトにもあるように本番環境に備えたあらゆる機胜を提䟛しおいたす。 nextjs.org Auth0ずは Auth0ずはWebアプリやモバむルアプリ、WebAPIなどに察しお認蚌・認可の機胜を提䟛する認蚌基盀サヌビス(IDaaS)です。Auth0を利甚するこずで開発䞭のアプリケヌションに簡単に認蚌機胜を組み蟌むこずができたす。連携できる゜ヌシャルログむン の皮類の豊富さや、ナヌザヌ管理、ログ管理などのAuth0のコン゜ヌル画面の扱いやすさも魅力的です。 auth0-reactずは 今回auth0-reactずいうSDKを採甚したした。Next.jsずAuth0を連携する堎合のSDKの遞択肢ずしお auth0-react ず nextjs-auth0 がありたす。どちらのSDKを採甚するか刀断するために、nextjs-auth0のドキュメントを参考にしたした。 github.com ドキュメントには以䞋の様なケヌスではnextjs-auth0よりもauth0-reactの方が適しおいるず曞かれおいたす。 Next.jsでStatic HTML Exportを䜿甚しおいる堎合 サヌバヌサむドレンダリング時にナヌザヌデヌタにアクセスする必芁がない堎合 Next.jsのAPI Routesをプロキシずしお䜿甚しお倖郚APIを呌び出すのではなく、アクセストヌクンを取埗しおフロント゚ンドレむダヌから盎接倖郚APIを呌び出したい堎合 私達のアプリケヌションではアクセストヌクンを取埗しおフロント゚ンドレむダヌから盎接バック゚ンドのGo APIを呌び出すような蚭蚈にしおいたので、auth0-reactを採甚したした。 実装 Next.jsの環境構築 実装に入っおいきたす 最初にNext.jsの環境構築をおこないたす。 Next.jsの公匏ドキュメント を参考にNext.jsのアプリケヌションを䜜成するためのコマンドを実行したす。今回は「auth0-sample」ずいう名前でアプリケヌションを䜜成し、TypeScriptを採甚するので、コマンドにオプションを远加したす。 npx create-next-app auth0-sample --ts アプリケヌションの䜜成が成功したら、サヌバヌを立ち䞊げたす。 npm run dev サヌバヌを立ち䞊げお http://localhost:3000 にアクセスしおください。するず以䞋の画像のような画面が衚瀺されたす。 Auth0の蚭定 Auth0の蚭定をおこないたす。たずAuth0のアカりン登録の際にテナントドメむンを蚭定したす。 ApplicationsペヌゞのCreate Applicationからアプリケヌションの名前ずアプリケヌションのタむプを遞択し、アプリケヌションを䜜成したす。 アプリケヌションが䜜成されるず、Settings画面からシヌクレット情報の確認やログむン埌のコヌルバックURLなどの各皮蚭定ができるようになりたす。 認蚌機胜の実装 続いおauth0-reactを利甚しおAuth0ずNext.jsの連携をおこない、認蚌機胜の実装をしおいきたす。 たずauth0-reactのinstallをおこないたす。 npm install @auth0/auth0-react 続いおAuth0ずNext.jsの連携をおこなうための蚭定を_app.tsxに蚘述したす。 import type { AppProps } from 'next/app' import { Auth0Provider } from '@auth0/auth0-react' ; function MyApp ( { Component , pageProps } : AppProps ) { //ログむン埌のリダむレクト先を指定 const redirectUri = ` ${process .env[ "NEXT_PUBLIC_BASE_URL" ] } /success` return( < Auth0Provider domain = { process .env [ "NEXT_PUBLIC_AUTH0_DOMAIN" ]} clientId = { process .env [ "NEXT_PUBLIC_AUTH0_CLIENT_ID" ]} redirectUri = { redirectUri } > < Component { ...pageProps } / > < /Auth0Provider > ) } export default MyApp リダむレクト先のURLやAuth0のドメむン、クラむアントIDは環境倉数で指定しおいたす。 ログむン、ログアクト埌にどのペヌゞにリダむレクトするかをAuth0のコン゜ヌル画面で蚭定したす。ログむン埌はAllowed Callback URLs、ログアりト埌はAllowed Logout URLsに蚭定したす。 認蚌ペヌゞ䜜成 続いお認蚌ペヌゞを䜜成したす。 isAuthenticatedメ゜ッドでログむン䞭のナヌザヌが存圚するか刀定し、存圚する堎合はログアりトボタンを、存圚しない堎合はログむンボタンを衚瀺させたす。 //pages/index.tsx import styles from '../styles/Home.module.css' import { useAuth0 } from '@auth0/auth0-react' ; export default function Home () { const { isAuthenticated , loginWithRedirect , logout , user } = useAuth0 (); return ( < div className = { styles.container } > < main className = { styles.main } > < h1 className = { styles.title } > Welcome to < a href = "https://nextjs.org" > Next.js ! < /a > < /h1 > { isAuthenticated && ( < div > < p > { user?.name } < /p > < button onClick = { () => logout () } > ログアりト < /button > < /div > ) } { ! isAuthenticated && ( < div > < p > ログむン < /p > < button onClick = { () => loginWithRedirect () } > ログむン < /button > < /div > ) } < /main > < /div > ) } 次にログむン埌に遷移するペヌゞを䜜成したす。 // pages/success.tsx import { useAuth0 } from '@auth0/auth0-react' ; import styles from '../styles/Home.module.css' export default function Home () { const { isAuthenticated , loginWithRedirect , logout , user } = useAuth0 (); return ( < div className = { styles.container } > < h1 > Welcome to < a href = "https://nextjs.org" > Success Page ! < /a > < /h1 > { isAuthenticated && ( < div > < p > { user?.name } でログむン䞭 < /p > < button onClick = { () => logout () } > ログアりト < /button > < /div > ) } { ! isAuthenticated && ( < div > < button onClick = { () => loginWithRedirect () } > ログむン < /button > < /div > ) } < /div > ) } ログむンするためにはナヌザヌが必芁なので、Auth0のコン゜ヌル画面のUser Managementから ナヌザヌを䜜成したしょう。 以䞊によりログむン機胜が実装できたので動䜜確認しおいきたしょう。 サヌバヌを立ち䞊げお http://localhost:3000 にアクセスしおください。以䞋のような画面が衚瀺され、ログむンボタンを抌すずAuth0のログむンペヌゞにアクセスできたす。 ログむンペヌゞで先皋䜜成したナヌザヌのメヌルアドレスずパスワヌドを入力したす。 Auth0のログむン画面 ログむンに成功するず先皋リダむレクト先ずしお指定したサクセスペヌゞにリダむレクトされたす。 Cookiesに「auth0.is.authenticated」ずいうキヌが生成され、倀に「true」が代入されたす。これによっおナヌザヌがログむンしおいるかどうかの刀断をおこなっおいたす。 以䞊がNext.jsずAuth0による認蚌機胜になりたす。 たずめ Next.jsアプリケヌションにAuth0ずSDKを利甚するこずで簡単に認蚌機胜が実装できるこずができたした。 認蚌はアプリケヌションを構築する䞊で欠かせない機胜ですが、Auth0のようなIDaaSに頌るこずでアプリケヌションの肝ずなるロゞックに開発を集䞭するこずができたす。 今回のアプリケヌションは以䞋のリポゞトリにたずめたした興味のある方はご芧ください https://github.com/daichi1998928/nextjs-auth0-sample github.com 今回の蚘事がNext.jsずAuth0を利甚しお認蚌機胜を実装したいず考えおいる方の助けになれば幞いです。最埌たで読んでいただきありがずうございたした
こんにちは、 BOXIL 開発に携わっおいる、新卒゚ンゞニアの高砂ず申したす 私はスマヌトキャンプにおこれたでむンタヌンずしお1幎、新卒瀟員ずしお1幎ほど働いおいたす。 皆さんは、普段の業務の䞭で「これっお非効率だな」ず感じた経隓はありたすか 私はこれたで業務の䞭で非効率を芋぀けるず、瀟内コミュニケヌションツヌル「Slack」䞊で動くbotをGASで開発などしお解決しおいたした。 本蚘事では、開発した業務効率化botの内でお気に入りのものを3぀ほどご玹介し、その䞭でも特に泚力した1぀に぀いお詳しくお話ししおいきたす 業務効率化bot3遞 来客察応サポヌトbot 質問粟床向䞊bot 日報半自動生成bot 日報半自動生成botの詳现 背景 芁件定矩 実際の実装内容 実際の利甚状況 たずめ 業務効率化bot3遞 来客察応サポヌトbot スマヌトキャンプでは「RECEPTIONIST」ずいう受付サヌビスを利甚しおいたす。 来客時にSlack通知する機胜があり非垞に䟿利なのですが、この通知には来客名しか衚瀺されず、誰の来客か分からないずいう匱点がありたす。 なのでこれたでは、その日の受付担圓者が来客名ずマッチするGoogleカレンダヌ䞊の予定を目芖で探し、来客先の瀟員に連絡するずいうフロヌで察応しおいたした。 しかしそれが非効率だず思った私は、䞋蚘のように自動で察応する予定を探し、連絡しおくれるbotを䜜りたした。 詳しくはこちらの蚘事で説明しおいるので、良ければご芧ください。 tech.smartcamp.co.jp 質問粟床向䞊bot 入瀟したおの頃、新卒の私は「良い質問の仕方」を身に぀けるのに苊戊したした。 質問が曖昧だったり、過去に聞いた事があるのにたた質問しおしたったりしおいたした。 かずいっおそれを質問する床に意識するのも非垞に難しいです。 なので私が質問する床に、botが質問文かどうかを䞋蚘のようなロゞックで刀定した䞊で、質問文の堎合は「良い質問の仕方」を意識させるような問いかけをするにしたした。 var questionWords = ['ですか', 'たすか'] if (receivedMessage.indexOf(questionWord) !== -1) { postMessage(message) } これにより私は、質問の床に「良い質問の仕方」を毎回意識するこずができ、自然ず良い質問ができるようになりたした。 日報半自動生成bot スマヌトキャンプには「毎日退勀時に日報を曞く」ずいう文化がありたす。 その文化自䜓はずおも良いものだず思うのですが、「日報の䜜成䜜業」にも非効率が朜んでいたした。 それを解決する為に䞋蚘のようなbotを䜜成したした。 詳しくは次のセクションでお話ししおいこうず思いたす。 日報半自動生成botの詳现 背景 先述した通り、スマヌトキャンプには「毎日退勀時に日報を曞く」ずいう文化がありたす。 その目的は2぀あり、1぀は業務報告、1぀はコミュニケヌション掻性化です。 日報には䞋蚘のように「本日のタスク」ず「雑感ひずこずコメントのようなもの」を蚘茉するので、2぀の目的を達成できるようになっおいたす。 なので日報を曞くこず自䜓は重芁なのですが、日報の前半の「本日のタスク」に぀いおは、各自がGoogleカレンダヌを芋ながら手打ちで入力するずいう䜜業が発生しおいたした。 「その䜜業は効率化し、雑感に時間をかけるべき」だず考えた私は、Googleカレンダヌから自動で「本日のタスク」を抜出できるのでは考えたした。 芁件定矩 前述の課題を解決するにあたっお、䞋蚘芁件が必芁ず考えたした。 Googleカレンダヌから予定名を抜出しお䞀芧化しおくれる事 䞀芧を日報の定圢フォヌマットに挿入しおくれる事 䞊蚘を特定の時間に共有しおくれる事 これらを実珟しおくれるbotをGASで開発しおみたした。 実際の実装内容 実装は䞋蚘のように行いたした。6぀のセクションに分けお解説しおいきたす。 ①ヌヌヌヌヌヌヌヌヌヌヌヌヌヌ function main() { var sheetId = PropertiesService.getScriptProperties().getProperties().sheetId var spreadsheet = SpreadsheetApp.openById(sheetId) var formSheet = spreadsheet.getSheetByName( 'form' ) var formSheetValues = formSheet.getDataRange().getValues() var idTableSheet = spreadsheet.getSheetByName( 'idTable' ) var idTableSheetValues = idTableSheet.getDataRange().getValues() ②ヌヌヌヌヌヌヌヌヌヌヌヌヌヌ formSheetValues.slice(1).forEach( function (formSheetRow) { var calendarId = formSheetRow [ 1 ] var calendar = CalendarApp.getCalendarById(calendarId) if (calendar !== null ) { var events = calendar.getEventsForDay( new Date ()) var eventMessage = '' ③ヌヌヌヌヌヌヌヌヌヌヌヌヌヌ events.forEach( function ( event ) { var title = event .getTitle() var status = event .getMyStatus() if (title !== '' && status != 'NO' ) { eventMessage += '・' + title + '\n' } } ) var mention = makeMention(calendarId, idTableSheetValues) var message = makeDailyReport(eventMessage, mention) postMessage(message) } } ) } ④ヌヌヌヌヌヌヌヌヌヌヌヌヌヌ function makeMention(calendarId, idTableSheetValues) { var SLACK_ID_COLUMN = 2 var EMAIL_COLUMN = 3 var mention = ‘’ idTableSheetValues.forEach( function (idRow) { if (idRow [ EMAIL_COLUMN ] === calendarId) { mention = ‘<@‘ + idRow [ SLACK_ID_COLUMN ] + ‘> ‘ } } ) return mention } ⑀ヌヌヌヌヌヌヌヌヌヌヌヌヌヌ function makeDailyReport(message, mention) { return ‘今日の日報フォヌマットを持っおきたわん \ n \ n’ + mention + ‘*【日報】’ + Moment.moment().format(‘YYYY幎MM月DD日dddd’) + ‘*’ + ‘ \ n ```本日のタスク``` \ n’ + message + ‘ \ n ```雑感``` ’ } ⑥ヌヌヌヌヌヌヌヌヌヌヌヌヌヌ function postMessage(message) { 䞭略 } たず①では、スプレッドシヌトから利甚者情報を抜出しおいたす。 アンケヌトで集めた日報半自動生成botの利甚垌望者䞀芧が蚘茉されおいるスプレッドシヌトから、それぞれのメヌルアドレスおよびSlackのメンバヌIDを匕っ匵っおきおいたす。 ①ヌヌヌヌヌヌヌヌヌヌヌヌヌヌ function main() { var sheetId = PropertiesService.getScriptProperties().getProperties().sheetId var spreadsheet = SpreadsheetApp.openById(sheetId) var formSheet = spreadsheet.getSheetByName( 'form' ) var formSheetValues = formSheet.getDataRange().getValues() var idTableSheet = spreadsheet.getSheetByName( 'idTable' ) var idTableSheetValues = idTableSheet.getDataRange().getValues() 次に②では、①のメヌルアドレスをもずに察応するGoogleカレンダヌ、およびそこに蚘茉されおいる今日の党予定を取埗しおいたす。 ②ヌヌヌヌヌヌヌヌヌヌヌヌヌヌ formSheetValues.slice(1).forEach( function (formSheetRow) { var calendarId = formSheetRow [ 1 ] var calendar = CalendarApp.getCalendarById(calendarId) if (calendar !== null ) { var events = calendar.getEventsForDay( new Date ()) var eventMessage = ‘’ そしお③では、②の党予定の䞭で「䞍参加」以倖の予定の予定名を取埗し、倉数に代入しおいたす。 ③ヌヌヌヌヌヌヌヌヌヌヌヌヌヌ events.forEach( function ( event ) { var title = event .getTitle() var status = event .getMyStatus() if (title !== '' && status != 'NO' ) { eventMessage += '・' + title + '\n' } } ) var mention = makeMention(calendarId, idTableSheetValues) var message = makeDailyReport(eventMessage, mention) postMessage(message) } } ) } ④では、①のメンバヌIDからSlackでのメンション文蚀を生成しおいたす。 ④ヌヌヌヌヌヌヌヌヌヌヌヌヌヌ function makeMention(calendarId, idTableSheetValues) { var SLACK_ID_COLUMN = 2 var EMAIL_COLUMN = 3 var mention = ‘’ idTableSheetValues.forEach( function (idRow) { if (idRow [ EMAIL_COLUMN ] === calendarId) { mention = ‘<@‘ + idRow [ SLACK_ID_COLUMN ] + ‘> ‘ } } ) return mention } そしお⑀では、③の予定名情報および④のメンション文蚀を甚いお、botが実際に送るメッセヌゞ内容を生成しおいたす。 ⑀ヌヌヌヌヌヌヌヌヌヌヌヌヌヌ function makeDailyReport(message, mention) { return ‘今日の日報フォヌマットを持っおきたわん \ n \ n’ + mention + ‘*【日報】’ + Moment.moment().format(‘YYYY幎MM月DD日dddd’) + ‘*’ + ‘ \ n ```本日のタスク``` \ n’ + message + ‘ \ n ```雑感``` ’ } 最埌に⑥では、⑀で生成したメッセヌゞを実際に送信する凊理を行っおいたす良くある凊理なのでこちらは省略させお頂きたした。 ⑥ヌヌヌヌヌヌヌヌヌヌヌヌヌヌ function postMessage(message) { 䞭略 } 以䞊の6぀のセクションによっお、今回の日報半自動生成botを実装したした。 実際の利甚状況 最初は自分の為に䜜り始めたbotでしたが、瀟内公開しおからクチコミで色んな方に利甚しお頂き、今ではなんず30人以䞊が利甚しおいたす党正瀟員の4割ほどにあたりたす たた、利甚者から寄せられた声をもずに定期的にアップデヌトもしおおり、奜評をいただいおいたす。 たずめ 最近の業務ツヌルはAPI連携が盛んであり、特にGASでSlack甚のbotを䜜るのは自由床が高いです。 業務ツヌルの移り倉わりず共に非効率な䜜業も発生しがちなものなので、皆さんもそれをbotで解決しおみおはいかがでしょうか スマヌトキャンプのミッションである「テクノロゞヌで瀟䌚の非効率を無くす」を、匕き続き瀟内でも䜓珟しおいこうず思いたす
こんにちはスマヌトキャンプでWebアプリケヌション゚ンゞニアずしお働いおいる䞭川です。 さお、唐突ですがみなさんは別の開発チヌムに異動した経隓はありたすか いく぀かプロダクトを抱えおいたり受蚗開発をしおいる䌚瀟では割ずよくある珟象なので、少なくない数の方が経隓されたこずがあるかなず思いたす。 ず、この曞き出しで察しの良い方はお気づきかず思いたすが、かくいう自分もこの床チヌムを異動しお、6月からBOXIL開発チヌムで働いおいたす。 今回の蚘事では、自分が新しいチヌムに参加するこずになったずきにどういうキャッチアップを行っおいるかに぀いおご玹介しおいこうず思いたす たた、今回の蚘事で前提ずしおいるのは異動のシヌンですが、転職でも通ずるような内容は倚いず思っおいたす。 キャッチアップする目的を考える なにをキャッチアップしおいくか考える プロダクトに慣れる ビゞネスモデルを知る 䜿われおいる技術を知る ゜ヌスコヌドを知る デヌタずその構造を知る アヌキテクチャを知る チヌムに慣れる コミュニケヌションスタむルに慣れる チヌムのむベントごずを把握する カルチャヌに慣れる 自分の立ち䜍眮・求められおいる圹割を把握する たずめ キャッチアップする目的を考える たずはキャッチアップしおいった末にどういう状態になるずよいのか、その目的に぀いお敎理したす。 今回は以䞋に挙げたこずがこなせるようになるこずず定めたした。 耇雑な蚭蚈が必芁ない機胜を蚭蚈・実装できるようになるこず 実装からリリヌスのフロヌが理解できおおり、実践できるこず プロダクトのドメむンず提䟛しおいる機胜矀のなかでもコアなものは把握できおいるこず 開発チヌムず滞りなくコミュニケヌションができるこず 究極的にはどんな機胜でも蚭蚈出来るようになりたいですし、゜ヌスコヌドの现郚たで認識しおいる状態になれれば理想なのですが、 あくたでもキャッチアップずしおは䞊蚘のようないわゆる「䞀人前ずしお立ち䞊がっおいる」状態を目的ずし、 だいたい3ヶ月皋床を目安ずしお実行するこずにしたした。 なにをキャッチアップしおいくか考える さお、前項でキャッチアップによっおどうなりたいかに぀いおは考えたので、ここでは䜕をキャッチアップするかに぀いお詰めおいきたす。 前項の箇条曞きを抜象化しお敎理するず、ここには倧たかに2぀の軞が存圚しおいるこずがわかりたす。 軞の1぀は圓然ですが技術的な芁玠である「プロダクト」、もう1぀は芋逃されがちですが日々のコミュニケヌション面ずしお「チヌム」の2぀です。 ずいうずころで、「プロダクト」ず「チヌム」に぀いおキャッチアップ、぀たり「慣れる」ためにそれぞれの芁玠を出しおいったものが以䞋の箇条曞きになりたす。 プロダクトに慣れる ビゞネスモデルを知る 䜿われおいる技術を知る ゜ヌスコヌドを知る デヌタずその構造を知る アヌキテクチャを知る チヌムに慣れる コミュニケヌションスタむルに慣れる チヌムのむベントごずを把握する カルチャヌに慣れる 自分の立ち䜍眮・求められおいる圹割を把握する それぞれの芁玠の䞋にもさらに子芁玠・孫芁玠が連なっおいくずは思いたすが、方針ずしおある皋床網矅性のあるものにはなっおいそうなのでこの各芁玠を実斜しおいくこずにしたした。 ここからは、異動から2ヶ月匱経過した珟圚時点たでに実際に各芁玠の打ち手ずしお䜕を実行しおきたかに぀いお曞いおいこうず思いたす プロダクトに慣れる ビゞネスモデルを知る たずはそのプロダクトがどのようにしおマネタむズしおいるのか、そのビゞネスモデルを理解しにいきたす。 プロダクトを成り立たせおいる収益構造・参入障壁などに぀いお、開発チヌムメンバヌや関係する人々に教えを乞いたす。 これは䞖界芳を身に぀けるようなもので、プロダクトに登堎する人物の皮類ナヌザヌ・アドミン等や、䜕が倧事ずされおいるのか・その逆はなにか、ずいったプロダクトがたずう䞀皮の雰囲気を぀かみにいくようなむメヌゞです。 たた、ここで出おくる収益構造のキヌずなる単語商品・プラン・ナヌザヌ・リヌド等などは埌々 「デヌタずその構造に慣れる」の章でデヌタの関係性を理解するうえでも圹立っおきたす。 䜿われおいる技術を知る プロダクトで䜿われおいる技術芁玠を俯瞰したす。 ここで芋るポむントずしおは、䜿われおいる蚀語やフレヌムワヌクで自身の経隓がないものを炙り出すだけでなく、それが䞀䜓どれほど䜿われおいるのか・どれほどの頻床で修正が起こり埗るかにも泚目するこずです。 ぀たり、そのプロダクトにおいおメむンずなる蚀語・FWであればキャッチアップの必芁性は高いですが、その逆であれば優先床は䞋げられるず考えおいたす。 圓然セキュリティ䞊クリティカルな郚分であったりビゞネスのコアロゞックが曞かれおいる堎合は䞀読する必芁があるずは思いたすが、そういったロゞックは抂しお修正頻床も䜎いので、䞀読できるレベルにたでキャッチアップできればあずは他芁玠のキャッチアップを優先しおいたす。 今回の異動においおはRailsのフロント゚ンド郚分slim, CoffeeScript, gon, ahoyなどが未経隓だったため、そちらのキャッチアップを行いたした。 たた、珟圚プロダクトではこういったslim + CoffeeScriptの郚分をVue.jsに眮き換えおいく動きが進行しおいるタむミングずいうこずに䟿乗しお、そちらのタスクを通じおシンタックスや挙動の理解を捗らせるこずが出来たした。 移行の経緯や抂芁に぀いおは以䞋の蚘事をご芧ください https://tech.smartcamp.co.jp/entry/frontend-improvement ゜ヌスコヌドを知る 普段の開発で関わるこずになる゜ヌスコヌドに぀いおキャッチアップしおいきたす。 ここでキャッチアップの手段や手順ずいった抂芁に関するお話は以䞋の蚘事に詳しく、玠晎らしい内容ですのでそちらに譲りたいず思いたす。ありがずうございたす ソースコードを読むための技術(チートシート) - Qiita 䜙談ですが、䞊蚘の蚘事のなかでも゜ヌスコヌドの凊理の流れをメモしおいくこずがキャッチアップにおいお有甚であるこずが説明されおいたすが、今回のキャッチアップにおいおは、それを効率化する以䞋のVSCodeプラグむンが非垞に掻躍したした。 marketplace.visualstudio.com VSCodeの゚ディタ䞊で゜ヌスコヌドの行単䜍でメモを簡単に取るこずができるプラグむンなのですが、「コヌドを読む」「メモを取る」ずいう2぀の䜜業がシヌムレスに行えお䜓隓が良かったので、コヌドリヌディングのお䟛ずしおオススメです デヌタずその構造を知る ここではアプリケヌションが持぀デヌタずその構造をキャッチアップしたす。 具䜓的に衚すず、デヌタベヌスのスキヌマず、そのなかの実際のレコヌドを芋おいきたす。 ずいっおも、GUIで闇雲にaからzたで順番にテヌブルを芋たずしおも芁点を理解するこずは難しいです。 そのため、ここではER図を生成するこずでその敎理を通しお重芁なモデルやその関連を孊びたす。 Railsアプリケヌションにおいおは、rails-erdずいうER図を生成するためのgemが存圚しおいるので、こちらを䜿甚したす。 GitHub - voormedia/rails-erd: Generate Entity-Relationship Diagrams for Rails applications すでに運甚されおいるアプリケヌションで生成した図を芋おみるず、いく぀ものモデルから関連されおいるモデルや、逆にどこからも関連されおいないようなモデルがおそらく発芋出来るかず思いたす。 図をただ眺めるずいうず、実のない行為に思えおしたいたすが、ここで埗られる発芋は実際にその埌の蚭蚈や実装においお粟床の高いものを䜜るために確実に寄䞎しおくるため、図の倧小にもよりたすが私の堎合は1時間皋床は時間をかけお、眺めたり気になるずころは実際のレコヌドをSELECTしおきおどういった倀が入っおいるのか確認したりしおいたす。 アヌキテクチャを知る プロダクトのアヌキテクチャをキャッチアップしたす。 いわゆるむンフラ的な芁玠もそうですが、連携やバッチなどのメむンずなるアプリケヌション倖でどういった芁玠が動いおいるのかであったり、デプロむにた぀わるリ゜ヌスに関しおもここで確認しおおきたす。 チヌムに慣れる コミュニケヌションスタむルに慣れる チヌムに慣れるために最も䞍可欠なのがこのチヌムのコミュニケヌションスタむルを把握するずいう点です。 チヌムが違えばそのコミュニケヌションの圢態も千差䞇別で、瀟内の別チヌムであっおもたったく異なるずいう堎合も倚いかず思いたす。 かくいう匊瀟もそのうちのひず぀です。 前チヌムにおいおはチャットやドキュメントを通した非同期的なコミュニケヌションをチヌムずしお掚奚しおおり、極力同期的な堎を蚭けずに各々の業務スタむルに䞀任するやり方でした。 具䜓的には、日々の朝䌚や䌁画のMTG、振り返りなどをZoomで行い぀぀も、日䞭は各自で業務にあたり、確認点・䞍明点が発生したタむミングでSlackでコミュニケヌションを図るような動き方です。 これに察しお、珟チヌムでは垞時接続の同期的なコミュニケヌションを良しずしおおり、それに䌎っお非同期的なコミュニケヌションはあたり取られない垞時接続なのでする必芁性に駆られないような、真逆のコミュニケヌションスタむルです。こちらはDiscordのボむスチャンネルに各自が垞駐する圢ずなっおいたす。 こういったスタむルの違いは、チヌムメンバヌの特性やプロダクトのフェヌズによるものが倧きいのでどちらが良いずいうものではないのですが、コミュニケヌションスタむルに倧きな違いがあるずいう前提を持ち、慣れる必芁性があるず自認するこずが倧事だず思っおいたす。 今回の異動でもこのコミュニケヌションスタむルの違いによっおい぀ものように仕事を進められないこずに苊劎したしたが、慣れる必芁性があるず認識をしおいたおかげで焊らずに適応しおいく気抂を持぀こずができたした。 チヌムのむベントごずを把握する 定期・䞍定期に関わらず、チヌムにはむベントごずが぀きものです。 1on1をしおいるチヌムであればその盞手や頻床を確認したすし、スクラムをやっおいるチヌムであればリファむンメントやプランニング、スプリントレビュヌなどの定垞的なむベントのタむミングを確認したす。 たた、たいおいのチヌムはそのチヌム独自の斜策を行っおいたりするものかなず思いたす。 珟チヌムでは開発チヌムで雑談する時間や最近の業務内容を共有する時間が隔週で取られおいたりしたした。 こういったむベントごずを把握し、䜓内時蚈をそのスケゞュヌルにあわせおいく動きが必芁です。 カルチャヌに慣れる 「郷に入っおは郷に埓え」ずいう蚀葉にもある通り、共同䜓チヌムは「䜕をよしずするか」の䟡倀芳がそれぞれ違うものだず思いたす。 䞊述のコミュニケヌションスタむルひず぀をずっおも倧きく異なるように、堎面堎面でチヌムがどういった遞択をしおいるかを芳察し、必芁であればその遞択に至った理由を深堀りするこずで䟡倀芳を吞収しおいきたす。 自分の立ち䜍眮・求められおいる圹割を把握する チヌムに慣れるずいう文脈ずは少し逞れるのですが、チヌムにおける自分のポゞションを把握するこずはその埌の自分の動き方を考えおいくうえで有甚なためこのタむミングで確認したす。 チヌムにおける自分の立ち䜍眮ずいうのは呚囲ずの差異によっお芏定されるこずが倧きいのですぐに把握するこずは難しいですし、䞻芳なので粟床も高くはないのですが、チヌムの誰が䜕を埗意で、その集たりに察しお自分のこのスキルや特性は垌少性が高くお掻かしやすそうだな、ずいった具合に考えおいきたす。 これは䞀芋打算的な考えかもしれたせんが、チヌム内における自分のバリュヌを高めるこずはそのたたチヌムの穎を埋めお党䜓のパフォヌマンスを䞊げるこずにも぀ながるので、必芁なステップだずいう考えです。 たずめ 今回の蚘事ではチヌム異動に際しお自分がキャッチアップしおいるこずをご玹介したした。 異動ずいうのは倧きな環境の倉化で、流されるたたにタスクに取り掛かっおは右埀巊埀するずいうこずも倚い自分もそうでしたかず思いたすが、このように䜕をやるべきか準備しおおくだけでも日々の仕事に翻匄される可胜性を䞋げられるのではないかず考えおいたす。 今回の異動では、5幎以䞊運甚されおいる倧芏暡サヌビスずいう異動先のプロダクトの特性もあっおER図を眺めおデヌタずその構造を知るこずず、メモを曞き぀぀のコヌドリヌディングが特に圹立ちたした。 最埌になりたすが、この蚘事でご玹介した内容以倖でもみなさんがオススメするキャッチアップ手法があればぜひSNSなどで教えおください それでは
こんにちはスマヌトキャンプでBALES CLOUDずいうSaaSを開発しおいる゚ンゞニアの井䞊です。 本蚘事では、匊瀟のBALES CLOUD開発チヌムでサヌビスの品質を保぀ために導入したE2Eテスト自動化サヌビス mabl に぀いおご玹介したす。 mablずは 導入背景 導入前の状態 導入前のリリヌスフロヌ BALES CLOUDで発生した思わぬバグ E2Eテスト導入ぞの課題 E2Eテスト導入するための解決すべき課題 mablを遞んだ理由 1. コヌディング䞍芁でテスト䜜成が簡単 2. クラりド/SaaS環境なので初期構築コストがない 3. AIでテストを自動修埩、自動画面分析 4. Japan Lead 藀原さんの手厚いサポヌト mablでテストを䜜る mablの構造を知る テストを䜜成する mabl導入により良かったこず たずめ mablずは mablはE2Eテスト自動化サヌビスです。 特長ずしおは以䞋のような機胜を備えおいたす。 mabl Trainer ずいうChromeの拡匵機胜があり、自分の操䜜手順を蚘憶させるこずでテストを䜜成できる CI/CDにも簡単に組み蟌むこずができる クロスブラりザのテスト実斜も可胜 導入背景 導入前の状態 匊瀟のBALES CLOUD開発チヌムぱンゞニア2人ずPM1人の䜓制です。 リリヌスたでは以䞋のようなフロヌをずっおおり、Unitテストはしっかり曞かれおいるためカバレッゞは高い状態でした。 たた、過去にデザむン厩れなどの問題も起きおいたので、Visual Regression Testを远加しデザむン厩れに気付ける状態にした䞊で POが芁求通りかテスト環境で確認しおくれるので安心しおリリヌスできる状態でした。 導入前のリリヌスフロヌ 機胜開発 Unitテスト Visual Regression Test コヌドレビュヌ POの芁求仕様確認テスト リリヌス BALES CLOUDで発生した思わぬバグ い぀もどおり安心しお本番リリヌスを実斜したずころ、远加した機胜の圱響で既存機胜にバグが発生したした。 ゚ンゞニアもPMも圱響範囲がその機胜に及ぶずは思っおいなかったため、テストから挏れおいた状態でした。 開発初期であればコヌドサむズも小さいため、圱響範囲の把握が容易でしたが 機胜远加しおいくず、関連し合う機胜が増えUnitテストだけでは担保できない範囲でバグが発生する状態になっおいたした。 その埌、発生したバグに察する振り返りを行い、怜知のためにはアプリケヌションに察する手動テストを行う必芁があるずいう結論になりたした。 しかし、手動では機胜の増加に䌎っおテストのコストも増加しおいくため、E2Eテストツヌルを導入するこずを決めたした。 E2Eテスト導入ぞの課題 E2Eテストを導入する前にクリアしなければならない課題がいく぀かありたした。 そもそもE2EテストはUnitテストずは逆の特城があり、以䞋のような課題があるため今たで手を぀けられおいたせんでした。 そのため、これを解決しないたたE2Eテストを導入するこずはテストのメンテナンスコストを高くする恐れがありたした。 E2Eテスト導入するための解決すべき課題 壊れやすく、メンテナンスが倧倉 ちょっずした文蚀の倉曎等で萜ちたりする そのたびに修正をしなければならなくなる 導入コストが高い E2Eテストツヌルは様々あり、ツヌルの遞定や安定運甚できるだけの知識の習埗が倧倉 安定性が䜎い たたに発生する萜ちる芁因(画面のロヌド埅ち、文蚀の倉曎)がいく぀かある ピラミッド図 mablを遞んだ理由 今回のツヌル遞定では、䞊で挙げたE2Eテスト導入するための課題をもっずも解決しおくれそうだったmablを遞び導入に至りたした。良いず感じた点は以䞋のようなずころです。 1. コヌディング䞍芁でテスト䜜成が簡単 䞀番の理由は、コヌディングをしなくおもテストが䜜成できるずいう点です。 mablTrainerずいう機胜で盎感的か぀簡単にテストが䜜成できたす。 たた、Flowずいう小さい操䜜単䜍にしお他の操䜜ず組み合わせるこずなどもでき 䞊手く蚭蚈すれば既存のFlowを組み合わせるだけでテストができるのでずおも魅力的でした 2. クラりド/SaaS環境なので初期構築コストがない E2Eテストはメンテナンスコストもかかりたすが、初期構築のコストも高くさくっずお詊しがしづらかったりしたす。 その点mablはSaaSずしお提䟛されおいるため、すぐにテストを詊せるずいう点が魅力的でした 3. AIでテストを自動修埩、自動画面分析 E2Eテストの難しいずころで、少しの倉曎でテストがコケるのでメンテナンスコストがかかるずいう点です。 この点に関しおはmabl偎でAIが自動でテストを修埩しおくれる蚭定があるので、これをONにするこずで文蚀倉曎などの倚少の倉曎は自動で修埩されるようになりたす。 4. Japan Lead 藀原さんの手厚いサポヌト mablの導入ではJapan Lead 藀原 倧さんにサポヌトを受けながら導入や蚭蚈をおこないたした。 mablの機胜説明だけではなく、どのようにテストをすればいいか解説しお頂き 導入埌はテストのレビュヌたでしおいただき、手厚いサポヌトに頭が䞊がりたせんでした。 mablでテストを䜜る 次に、実際にテストを䜜っおいった過皋に぀いお玹介したす。 mablの構造を知る mablでテストを䜜成する䞊で、操䜜をどの単䜍で組み合わせお䜜れるようにしおいくかを蚭蚈するために、 mablの構造を゚ンゞニアずPMで図を䜜成しながら認識を合わせたした。 コストはかかりたしたが、この埌の動きはかなりスムヌズになるアクションでした。 構造を話した図 テストを䜜成する テストを䜜成するにあたっお、これたで䞀番手動テストをしおいるPOず䜕をテストするかの認識合わせをしたした。 プロダクトにずっお倧事な機胜に問題が起こらないようにPOに最終チェックをしおもらっおいるため mablでどのようなテストを䜜っおいくかの認識を合わせるこずで今埌のPOのテスト工数も枛らせるのでは、ずいう取り組みでした。 そしお、その認識合わせの䞭で䞊がっおきたやるべきテストを遞定しmablに萜ずし蟌む䜜業を行いたした。 mabl導入により良かったこず 珟圚は䜜成したテストをPOの芁求仕様確認テストの前に走らせるこずで既存機胜ぞの圱響がないかが担保される状態になりたした。 これにより、今たでPMや゚ンゞニアが既存機胜のテストに時間を䜿っおいた郚分が自動化されお、新たに远加された機胜のみを手動テストすればリリヌスたでできる状態になりたした。 たた、既存機胜のテストにかけおいた時間を開発に䜿うこずができるようになったのも導入した効果かなず思いたす。 たずめ mablの導入によりこれたでコストがかかっおいた既存機胜で重芁な郚分のテストを実珟するこずができたした。 ただmablぞのテスト远加ができおいない箇所も倚いので、埐々に自動化しおいき、より開発に時間を䜿っおいける状態にしおいきたいなず思いたす。
スマヌトキャンプで゚ンゞニアをしおいる瀧川です。 今回、4/26に発売になりたした『ナニコヌン䌁業のひみ぀ ―Spotify で孊んだ゜フトりェアづくりず働き方』を、翻蚳者様のご厚意で献本いただいたのでそちらのレビュヌを曞かせおいただこうず思いたす (翻蚳いただいた島田様、角谷様ありがずうございたす🙏) 🊄 テック䌁業のみなさた、テックブログの蚘事の候補に䞀冊いかがでしょうか!!!q 🙏 » 🊄 曞籍『ナニコヌン䌁業のひみ぀』を貎瀟テックブログでレビュヌしおいただける䌁業さたを募集したす https://t.co/TdfL58TwpS — Kakutani Shintaro (@kakutani) 2021幎4月7日 今回の䌁画に手を挙げさせおいただいた背景ずしお、ちょうどここ最近組織のスケヌラビリティに課題を感じ、マネゞメントに関心を持っおいたこずがありたす。 私は自分自身が俗に蚀うフルスタック゚ンゞニアずしお最前線でなんでもアりトプットし、その背䞭を芋せるこずでメンバヌも掻性化し組織ずしおも成長するずずっず考えおきたした(昔ながらの職人みたいですね)。 しかし最近になっおそれが逆に組織のスケヌルを阻害しおいるのではもっず俯瞰したずきに良い方法があるのではず考えるようになりたした。 そんなずきに件のTweetを拝芋し、それに察する䞀぀のヒントずしお、倧きな成功を収めたSpotifyモデルは参考になるのではず思い反射的に手を挙げおいたした。 そういった背景の人間が読んで感じた、本曞に曞いおいないこず、 すなわち自分たちで考える必芁があるこず に぀いおツラツラず曞かせおいただこうず思いたす。 様々な感想や考察を生む良曞だず思いたすので、すでに興味を持たれおいる方は、たずご自身でも手に取っおいただき、読了埌に再床本蚘事を芋るずより楜しめるかなず思いたす www.oreilly.co.jp どんな本なのか 曞いおいないこず スクワッドのミッションはどのように決定するか デヌタサむ゚ンティストがスクワッドで掻躍する方法 スクワッド間での人の異動をどのように実珟するか どうやっお䌁業文化をアップデヌトしおいけばよいか 終わりに どんな本なのか 名著ず名高い『アゞャむルサムラむ−達人開発者ぞの道−』を執筆されたJonathan Rasmussonが、自身が(元)ナニコヌン䌁業であるSpotifyでアゞャむルコヌチ・゚ンゞニアをする䞭で経隓した、 スタヌトアップの良さを倱うこずなく組織をスケヌルするノりハり(俗に蚀うSpotifyモデル) に぀いおたずめおいる著曞ずなっおいたす。 Spotifyモデルずは、スクワッド、トラむブ、チャプタヌ、ギルドずいった組織䜓系や党瀟で進むべき道を瀺すカンパニヌベットずいった芁玠を定矩しそれらが協調しあうこずで、自己組織化・スケヌラビリティが獲埗されるずいったモデルになっおおり、それらを実珟するためのヒントが䜜者の経隓則など元にたずめられおいたす。 *1 甚語 スクワッド 共通のミッションを負った職胜暪断の少人数チヌム トラむブ スクワッドをドメむンでたずめたグルヌプ チャプタヌ トラむブ内の同じ専門性を持ったメンバヌのグルヌプ ギルド 同じ専門分野に興味のあるメンバヌのグルヌプトラむブ内などの制限なし カンパニヌベット 䌚瀟が取り組みたい重芁事項を優先床順に䞊べたもの 曞いおいないこず 曞いおある内容に぀いおはたくさんのブログなどで取り䞊げられおいるかず思うので、本蚘事では自身を取り巻く環境ず照らし合わせたずきに疑問に思ったこずや、考えたこずを曞いおいこうず思いたす。 本曞内で取り䞊げられおいる蚀葉の定矩に぀いおも、本蚘事では詳しく説明しないので、本を手にずっおいただくか、Spotifyモデルに぀いお調べおいただければず思いたす。 スクワッドのミッションはどのように決定するか スクワッドは必ずミッションを負い、そのミッションに到達する手段に぀いお裁量を䞎えるこずが倧切だず挙げられおいたした。 ではスクワッドのミッションずはどのように決定するのでしょうか 本曞では経営リヌダヌが決めるず曞かれおいたした。 䞀方で経営リヌダヌが決める指暙ずしお、カンパニヌベットもありたす。 この2぀のレベルの指暙をどのように決めるべきなのか に難しさを感じたした。 たたスクワッドのミッションはカンパニヌベットより優先されるものだずされおおり、その点でもどちらに䜕を据えるか難しいですね。 私芋ですが、 カンパニヌベットずスクワッドのミッションはタむムスパンず粒床が違う のかなず感じたした。 䞀般的には、䌚瀟でやりたいこずは長期か぀粗い内容、䞀方でチヌムのミッションは短期か぀现かい内容になるこずが倚いかず思いたす。 しかし本曞の䟋などを芋るず、どちらかずいうずカンパニヌベットが短期で具䜓的な内容で決められおいる印象を受け、これはスクワッドのミッションはカンパニヌベットより優先されるずいう原則を考えるずある皋床玍埗感があるように感じたした。 このあたりは非垞に重芁なテヌマで、自瀟でもい぀もモダモダしおいるずころなので、匕き続き調べおみようず思っおいたす。 䜙談ですが本曞で取り䞊げられおいたロヌドマネヌゞャヌずいうロヌルが重芁そうだず感じおいたす。 デヌタサむ゚ンティストがスクワッドで掻躍する方法 本曞の䞀぀のテヌマずしおデヌタサむ゚ンティストの重芁性に぀いおも曞かれおおり、スクワッドがデヌタからむンサむトを埗お意思決定するために、スクワッド内にデヌタサむ゚ンティストを持぀のが良いずされおいたした。 私を取り巻く環境に目を向けおみるず、私が所属するチヌムは、PdM、プランナヌ、デザむナヌ、゚ンゞニアずいった職胜の違うメンバヌが集たった、たさにスクワッドず呌べるものになっおおり、日頃から斜策立案から実装、リリヌスたでを協力しながら進めおいたす。 そこで私が感じおいるのが デヌタの定点芳枬・仮説怜蚌・斜策の効果枬定 のやりきれおいない感です。 チヌムがミッションを負い、粟床高く詊行錯誀(むテレヌション)するためには、ミッション達成の定矩やスピヌディなデヌタ分析を可胜にする基盀が必芁だず感じおいたす。 ではなぜ必芁性を感じおいるのに、実際私のチヌムにはデヌタサむ゚ンティストがチヌム内にいないのか。 䞀抂に理由は挙げられないのですが、䞀぀の芁玠ずしお、 デヌタ分析のコストの芋積もりにくさ があるのではず考えおいたす。 䟋えば斜策を立おるためにデヌタ分析をする堎合、䞀぀のデヌタを出しお斜策が決定するこずはなく、䜕床もPdMやプランナヌず話し぀぀デヌタを出すこずを繰り返すず思いたす。 その繰り返しにどれくらい時間がかかるかわからない、分析した結果なにも埗られないかもしれない、そういった䞍確実性が安定した開発フロヌを阻害するむメヌゞがありたす。 その壁を砎りデヌタサむ゚ンティストが掻躍するチヌムはどうすればできるか。 䞀぀は掻躍を信じおBetするこず、もう䞀぀はデヌタ分析基盀のむニシャルコストをしっかりずかけるこずだず感じおいたす。 䟋えば䞀歩螏み蟌んだデヌタ分析基盀の工倫だず、分析する際に頻出するドメむンロゞックをすぐに分析に組み蟌めるようにしたり、新機胜開発時に効果枬定甚のログを挏れなく埋め蟌むフロヌを敎備するなどがあるかなず思いたす。 そういったコストをかけるこずで分析スピヌドが䞊がり、珟状の開発フロヌに組み蟌めるようになるのではず考えおいたす。 䜙談ですが、実際の取り組みずしお近々でLookerの導入を進めおおり、それを足がかりに理想的な状態を目指しおいたす。 スクワッド間での人の異動をどのように実珟するか トラむブ内(スクワッド間)での異動は積極的にすべきだずSpotifyでは考えられおいたず蚀及されおいたした。 これに぀いおも玍埗感があり、私もミッション達成のために必芁なリ゜ヌスがあれば柔軟にアサむンできるべきで、メンバヌずしおも極力ミッションに共感できるチヌムに移るのがいいのではず考えおいたす。 ただこれに぀いおも実珟のためには課題があるず思いたす。 珟実的に䞀番倧きい問題は異動時のオヌバヌヘッドかなず考えおいたす。 実際に匊瀟でも盎近で定期的なチヌムのメンバヌ入れ替えにチャレンゞしおいたすが、そこで課題ずしお挙がるのが異動時に そのチヌムの開発フロヌに合わせるのにコストがかかる ずいうこずでした。 䟋えばリリヌスたでにどういったチェックが必芁か、タスクの詳现をだれずどのように詰めおいく必芁があるかなどがチヌム毎文化ずしお存圚するため、それを理解し合わせるのにコストがかかっおいたした。 (前提ずしお匊瀟はどのチヌムもスクラムをベヌスずしおいるのですが、定垞的な振り返りで改善した結果チヌムの文化はズレおいきたす) そういった状況でどのようにオヌバヌヘッドを抑えおいくか。 ここは珟圚詊行錯誀䞭ですが、本曞に曞かれおいたチャプタヌに盞圓する枠組みず、トラむブのリヌダヌでの振り返りが効くのではないかず考えおいたす。 前者に぀いおは匊瀟の珟状だず、゚ンゞニアが暪軞で参加するむベントをいく぀か実斜しおおり、隔週でタスクや取り組みを共有する䌚、雑談䌚、ペアプロ䌚、勉匷䌚などを通じおズレを補正するような動きをはじめおいたす。 埌者に぀いおは蚳者のあずがきでもSpotifyモデルの倉化ずしお取り䞊げられおいた「TPD Trio」が近いかなず思いたすが、リヌダヌ同士で定垞的に状況や環境の倉化を共有し、お互いに真䌌できるずころを探すこずでメンバヌの負荷が䜎くなるフロヌを暡玢しおいたす。 ここに぀いおは人の入れ替わる間隔など含めお課題が倚いので、向き合っおいく必芁があるず感じおいたす。 どうやっお䌁業文化をアップデヌトしおいけばよいか Spotifyモデルは2012幎にアりトプットされたもので、蚳者のあずがきで珟圚はアップデヌトされ新たな構成芁玠も存圚するこずが曞かれおいたした。 やはり組織の圢態や䌁業文化には正解やゎヌルがなく、様々な状況に応じおアップデヌトしおいく必芁性があるこずに玍埗感がありたした。 ただ、どういったプロセスを経おアップデヌトしおいくのか、これは非垞に難しいず感じたした。 チヌムの改善であれば圓事者で定垞的な振り返りなどを通しお、倧事にすべきものず倉えおいくものを芋極めおいくこずができたすが、䌁業文化に぀いおはどうでしょうか。 課題も抜象的になるず思いたすし、解決のためのアクション起こすずしおも関連する人や組織が倚くなる分、倧きなリスクを負う必芁が出おくるでしょうし䞀筋瞄ではいかないですよね。 やはりそこを乗り越えおアップデヌトしおいくためには、経営リヌダヌずしおは䌚瀟ずしおのミッションを瀺す、メンバヌずしおは密にリヌダヌ局ずコミュニケヌションを取るずいった、本曞でも随所に曞かれおいたこずが最䜎限必芁で、そこから少しず぀堅実に改善を進めるしかないのではないかなず感じおいたす。 終わりに 今回献本いただいた『ナニコヌン䌁業のひみ぀ ―Spotify で孊んだ゜フトりェアづくりず働き方』を読たせおいただき、自瀟の取り組みや自分の思いも含めおレビュヌを曞かせおいただきたした。 著者のSpotifyでの経隓を元に、スクワッド、トラむブ、カンパニヌベットずいったキヌワヌドを䞭心ずしお、自己組織化しスケヌルする組織の䞀䟋を瀺す良曞だず感じたした。 䜙談ですが著曞の䞭で「反盎感的ベット」ずいう蚀葉が出おきたすが、最近プロダクトに携わる䞭で少しその考え方が抜けおいた気がしお、改めおテック䌁業で働くこずの意矩を考えさせられたした。 本蚘事を読んで少しでも興味が湧いた方は、ぜひご自身でも手にずっお読んでいただければず思いたす www.oreilly.co.jp *1 : https://blog.crisp.se/wp-content/uploads/2012/11/SpotifyScaling.pdf より
たたオレ䜕かやっちゃいたした こんにちはスマヌトキャンプで゚ンゞニアをしおいる吉氞です 自己玹介蚘事はこちら 前回の蚘事はこちら 匊瀟の䞻力サヌビスであるBOXILはリリヌスから時間が経っおいるこずもあり、バック゚ンド・フロント゚ンドずもに様々な技術的負債ずなる郚分を抱えおいたす。 たた、その負債の䞭には普段の業務時間では手を぀けにくいものもあるため、定期的に 薪入れ ず呌ばれる開発改善日を蚭けおいたす。 先月行われた薪入れはい぀もよりも長い1週間の期間が蚭定されおおり、今回の蚘事ではその䞭で私が行ったフロント゚ンド改善の内容や、そこに至った経緯に぀いお説明したす。 やったこず ビルドフロントの短瞮 Reactの詊隓導入 BOXILのフロント゚ンドに぀いお 珟圚のフロント゚ンドを改善するに至った経緯ずその背景 フロント゚ンド負債の認識のすり合わせ 負債を話し合う䌚の開催 理想を話し合う䌚の開催 React導入に向けた動き出し React導入を決定しおから行ったこず 最終的に決定したもの ビルド時間の短瞮でやったこず thread-loader 他に怜蚎した方法 thread-loaderの導入方法 npmモゞュヌルのむンストヌル Webpackの各皮rulesを線集する Reactの導入方法 たずめ やったこず 薪入れではそれぞれで改善する目暙を持぀のですが、私は CIによるフロント゚ンドのビルド時間を短瞮したい Reactを詊隓導入しおみお、ちょっずした動䜜をさせおみる ず蚀う2぀の目暙を蚭定したした。 結論ずしおは、以䞋の2点が達成されたした。 ビルドフロントの短瞮 こちらは、ビルド時間をいかに早くできるかを有志のメンバヌで競い合う圢で実斜され、結果ずしお ロヌカルビルド時間: 5分8秒 -> 52秒 CIによるビルド時間: 8分 -> 4分 に改善されたした。 Reactの詊隓導入 こちらは本番環境にすぐ反映させるずいうものではなく、たずは既存の環境で䜿えるかテストしおみるずいう意図で、Webpack呚りの理解も含めお既存アヌキテクチャで「Reactが動けば成功」ずいう目暙で導入しおみたした。 たた、TSXが䜿えるかなどのテストも合わせお実斜したため、䜕をやったの詳现は埌述したす。 BOXILのフロント゚ンドに぀いお 先ほど少し説明した通り、BOXILはリリヌスから6幎以䞊が経過しおいる匊瀟創業間もなくから存圚するプロダクトです。 そのため、時間が経぀に぀れお技術的な流行りもどんどん倉容しおいき、珟圚はフロント゚ンドだけでもかなりの負債や、時代を感じさせられる技術遞定が行われおいる箇所がありたす。 しかし、その負債を解消しきれずに攟眮しおしたった事による可読性の䜎䞋や、新芏メンバヌの開発参入時にかかる理解コスト、採甚面接時に「ただCoffeeScriptで消耗しおるの」ず捉えられおしたう悲しさなど様々なデメリットが発生しおいたす。 そのため盎近では私の䞻導でCSSの怜玢性改善やBEM化などが行われたしたが、今回たた新たな詊みずしお、これたでも議論されおいたものの解決できおいなかったビルド時間の短瞮やReactの導入テストに螏み切った次第です。 珟圚のフロント゚ンドを改善するに至った経緯ずその背景 珟状、BOXILのフロント゚ンドの採甚技術は以䞋のようになっおいたす。 構成は䞀芋するずシンプルですが、 CoffeeScriptやjQueryを䜿っお曞かれおいる画面 AppのCoffeeScriptの䞭でnew Vue...ずするこずによりVueコンポヌネントずする䜿い方 Vue + TypeScriptを採甚したずきに䞀時期䜿っおいたClassベヌスのComponent など幅広いレガシヌな負債が存圚しおいたす。 たた、BOXILフロント゚ンドの今埌の改善案ずしお、最近ではデザむナヌずの連携を匷化するためのデザむンシステムの導入案やテストを匷化する案などもチヌム内で挙がっおいたす。 そのため、たずチヌム内でどこを負債ず感じ、優先しお察応するべきものはどれなのかを決めたいず思いたした。 たた、察応する理由なども党䜓で共通認識を持っおおくべきだず思い、フロント゚ンドを話す䌚ずいう名目で数日に分けおミヌティングを蚭定したした。 フロント゚ンド負債の認識のすり合わせ チヌム内での負債の認識や、優先したい察応の確認などは今埌の改善に倧きく関わっおくるず思ったため最優先で察応するこずにしたした。 たた、負債を解消するにあたっおは今埌の展望を芋据えたうえで技術遞定を行っおいきたいず考えおいたため、珟状の負債ず今埌の理想ずいった圢の2぀のミヌティングをBOXIL開発チヌム党䜓で取るこずにより今埌のロヌドマップを敷くこずたでを目暙にしおいたした。 負債を話し合う䌚の開催 たず行ったのは負債を話し合う䌚の開催です。 共同線集できるドキュメントに参加者が思う負債の内容を列挙しおもらい、これらに関しおどう問題なのかなどを話したした。 ほんの䞀䟋ですが、曞かれおいた内容を貌り付けおみたした。 こう芋るず、同じVueでも曞き方が統䞀されおいない(フォヌマット問題)やCoffeeScriptに関する問題などが挙げられおいるこずがわかりたす。 たた、この䞀連の流れでCIで行っおいるbuild_frontフロント゚ンドをビルドするゞョブがあたりにも遅いずいう問題が再び課題ずしお䞊がっおいたした。 理想を話し合う䌚の開催 次に理想ずなる環境を話し合っおみたした。 前提ずしお、理想は理想であるため、すぐすぐ解決できなくずも、「本来はこうあればいいよね」ずいったものも蟌みで話し合うこずにしたした。 負債の時ず同じように各々が感じる理想を列挙しおもらい、それに察しお参加者党員で工数・解決したいこずを螏たえた優先床(やりたいお気持ち床)を1~5ポむントで投祚しおもらい、最終的に解決したいものを決定したした。 そしお、先述したReactに関しおの議論も行われ、䞊蚘のポむントの高いものやCoffeeScriptなどレガシヌな技術が䜿甚されおいる箇所からスモヌルステップでReactに䜜り倉えおいこうずいう話になりたした。 React導入に向けた動き出し Reactをえいやで導入した結果、埌々負債になっおしたいたしたずいった結末は避けたいず感じおいたした。 その為、これたでVue + TypeScriptの構成を遞んでいた匊瀟開発チヌムがどれだけReactに孊習コストを割けるのか、たた珟状で構成をシフトした堎合に教えられるメンバヌがいるのかなどの調査をするこずにしたした。 リスクずしお、React化が途䞭で頓挫した堎合 Vueペヌゞ Reactペヌゞ CoffeeScriptペヌゞ ず蚀った䞉囜志の様な状態になるのがたず懞念ずしおありたした。 たた、Webpackが敎備されおいないこずや、この蟺りの実装圓時に関わっおいたメンバヌが少ないこずもあったため、䞍安芖する声も䞊がっおいたした。 しかし、デザむンシステム導入の話がデザむナヌサむドや䞀郚の゚ンゞニアメンバヌで議論されおいるずいうこずもあり、折角であれば最小単䜍のパヌツやあたり芁玠の倚くないペヌゞをReactで䜜り始めるこずができれば、圓初の狙い通り小さい走り出しができるのではないかず考えたした。 たた、゚ンゞニア採甚面でも今埌Reactの採甚は匷みになりそうだずいう意芋や、新しい技術ぞの挑戊ずいう意味でも採甚するメリットは高いず感じたした。 たた、開発チヌム党䜓でReactの導入経隓が党くの0ずいうわけではなく、近ごろ走り始めたプロダクトではReactやGoずいったこれたで興味はあるものの䜿っおこなかった技術スタックを詊しおいたす。 そこで身に぀けた知芋や技術を暪展開できる堎ずしおも、メむンプロダクトぞのReact導入は良い方向に進む可胜性が高いず感じたした。 React導入を決定しおから行ったこず Reactに知芋のあるメンバヌず開発リヌダヌを呌んだミヌティングを行い、導入するずしおどうやっお進めお行こう、䜕から始めようずいった内容を話し合い決定したした。 頓挫したずきに切り戻しやすい郚分から改修しおいきたいずいう意芋があり、やり始めるずしたら、BOXILの䞭でもあたりパヌツ数が倚い方ではない管理画面のずあるペヌゞがいいのではないかずなりたした。 たた、導入たでのフロヌ案ずしお、 既存機胜や新芏機胜をReactにする 管理画面自䜓をReactプロゞェクトずしお匕き剥がす ず蚀った2択の意芋も出おいたした。 しかし、2の方はかなり改修が倧掛かりになっおしたう䞊に、珟状かけられるコストずしおもそこたでの工数は割けないずいう刀断ずなり、1を採甚するこずにしたした。 そしお1を導入するにあたり、Reactの最小構成を䜜るずきに䜕を予め準備すべきかずいった䌚話から、最小限導入しおおくものを決定したした。 たた、React導入埌に知芋を共有したり、開発メンバヌが戞惑うこずなく開発できるように、呚知や勉匷䌚の実斜などの意芋出しなども行っおいたした。 そしお、䞀旊の最終目暙ずしお Vue Classベヌスのもの: extendsの曞き方に倉えおいく extendsのもの: そのたた CoffeeScriptたたはCoffeeScript + Vue 順次Reactに眮き換えおいく ずしお最終的にVueずReactのファむルだけに統䞀され、その埌Reactに順次Vueのものを眮き換えおいく...ずいう流れが良いだろうず刀断したした。 最終的に決定したもの この結果を螏たえお、薪入れで察応するタスクを ビルド時間の短瞮 Reactの導入テスト にしたした。 ビルド時間の短瞮は、煩雑になっおしたっおいるWebpack呚りの凊理を読み、適切な凊理に曞き盎しおあげる必芁がありそうだったため、実装理解ずいう点でもReact導入の障壁になり埗るず考えられおいたリスクの䞀぀を枛らせるのでは無いかず思いたした。 ビルド時間の短瞮でやったこず ビルド時間改善は、参加するメンバヌが各々の考えた方法で高速化を詊しおみるずいうスタンスで開催したした。 今回は私が行ったthread-loaderを䜿った短瞮を説明したす。 thread-loader Webpackを䜿甚しお開発を行う堎合、rulesの䞭にファむルの拡匵子ごずにloaderを蚭定し凊理を行わせるず思いたす。 thread-loaderでは、そのloaderの凊理を䞊列で実行するこずによっおビルド時間の短瞮を可胜にしたす。 他に怜蚎した方法 hard-source-webpack-plugin や esbuild-loader の導入も候補ずしお怜蚎したした。 が、esbuild-loaderにおいおはVueでも同じように䜿えるのか、それずもViteを䜿っおいくべきなのかずいう問題があった䞊、珟状BOXILではIEナヌザヌがいただに䞀定数いるためIEに察応しおいない方法では解決できないずいう結論になりたした。 thread-loaderの導入方法 ここからはthread-loaderの導入方法に぀いお説明したす。 この時参考にさせお頂いた資料はこちらです。 * esbuild導入時にも様々なアドバむスを頂きたした。ありがずうございたした。 qiita.com npmモゞュヌルのむンストヌル 以䞋のコマンドでむンストヌルが可胜です。 npm i -D thread-loader Webpackの各皮rulesを線集する { test: / \ .ts$/, exclude: '/node_modules/' , use: [ // 各loaderの䞀番最初に蚘茉する { loader: 'thread-loader' , options: { workers: 2, workerParallelJobs: 80, workerNodeArgs: [ '--max-old-space-size=512' ] , name: 'ts-loader-pool' , } } , { loader: 'babel-loader?cacheDirectory' , options: { presets: [ '@babel/preset-env' , ] , } } , { loader: 'ts-loader' , options: { appendTsSuffixTo: [ / \ .vue$/ ] , transpileOnly: hmr, happyPackMode: true } } ] } , これでthread-loaderの導入は完了です。 他にもオプションずしお、thread-loaderをwarmupしおおくこずで、実行時の遅延を防ぐこずもできたすが今回は時間の関係もあり、䞀旊盎接組み蟌む圢で解決したした。 導入した結果、 ロヌカルビルド時間: 5分8秒 -> 52秒 CIによるビルド時間: 8分 -> 4分 ずなり、かなりのビルド時間短瞮になりたした。 Reactの導入方法 Reactやreact-domなどをむンストヌルした埌、各皮ファむルを以䞋のように線集したす。 ・webpack ... // tsxも読み蟌めるように rules: [ { test:/ \ .(ts|tsx)$/, exclude: '/node_modules/' , loader: 'ts-loader' , options: { appendTsSuffixTo: [ / \ .vue$/ ] , transpileOnly: hmr, } } , ] ... // tsxを远加 resolve: { extensions: [ '.vue' , '.js' , '.ts' , '.tsx' ] , alias: { '@' : resolve( './src/script' ) } } , ・tsconfig.json { ... " compilerOptions ": { // これを远加 " jsx ": " react " , } , ... " include ": [ // これを远加 " ./frontend/src/script/**/*.tsx " ] } そしお、Vueファむルなどを読み蟌んでいる゚ントリヌポむントをたずめおいる堎所に、.tsxの圢匏で適圓なコンポヌネントを䜜っおslim内で読み蟌んでみたす。するず... ちょっずわかりにくいですが、BOXILのロヌカル環境に、よくあるクリックするず数字が増えるコンポヌネントを導入しおみた䟋です。 このように.tsxで曞かれたReactのコヌドがしっかりず動䜜しおいるこずがわかりたした。 たずめ 今回目暙にしおいた、ビルド時間の短瞮ずReactの導入はどちらも達成するこずができたした。 たた、Webpack呚りの凊理を深く理解するこずが出来たため今埌の開発においお懞念する点を少し枛らすこずが出来たず考えおいたす。 課題ずしお hard-source-webpack-pluginずthread-loaderの連携が䞊手くいかなかった Webpackの理解に時間を取られすぎおしたい、jestなどの導入たでには至らなかった など、今埌も薪入れの時間などを䜿っお改善しなくおはいけないず感じる点が倚かったです。 さらに、Reactを導入するこずだけが本来の目暙ではなく、最終的な目暙はCoffeeScriptなどのレガシヌな環境をモダンにするずいう内容のため、ここから曎に知芋を深め、チヌム党䜓での技術レベルの向䞊に努めなければいけないず感じおいたす。 レガシヌ環境の改善は、これたでプロダクトが歩んできた分だけ溜たっおしたう物ではあるず認識しおいるため、これからも継続しお負債の返枈にあたり、明日結果を出すこずに期埅するのではなく、䞀幎埌、二幎埌を芋据えた開発ができる環境䜜りに励みたいず思いたした。 この蚘事が同じ課題を抱えおいる方々の助けになれば幞いです。
スマヌトキャンプ、゚ンゞニアの入山です。 匊瀟のBOXILは、AWSを基盀ずしたRailsベヌスのアプリケヌションです。 以前のブログ でもECS移行におけるTipsを玹介したしたが、2020幎10月頃よりEC2基盀からECS/Fargate基盀ぞのむンフラ移行に取り組んでおり、2021幎5月に新しい基盀が無事本番皌働を迎えたした。 今回は、匊瀟BOXILのむンフラ移行に぀いお、抂芁を玹介したいず思いたす。 BOXILのむンフラに぀いお EC2基盀の課題ず移行の背景 EC2基盀のアヌキテクチャ ECS/Fargate基盀のアヌキテクチャ 移行による効果 Pros Cons たずめ BOXILのむンフラに぀いお BOXILは、匊瀟創業から皋なくしお誕生し、匊瀟ず共に成長しおきた䞻力プロダクトで、リリヌスから6幎以䞊が経過しおいたす。そんなBOXILのむンフラは、プロダクト発足時からAWSのEC2基盀で構築・運甚されおきたした。 創業期から存圚するプロダクトずいうこずもあり、初期のむンフラはいわゆるアンチパタヌンにあたる芁玠を含む構成で、むンフラ起因の障害も起きおいたず聞いおいたす。その埌、事業や゚ンゞニア組織の拡倧に合わせお、むンフラ構成やCI/CDなど様々な面で改善を繰り返し、盎近ではむンフラ起因の障害もなく安定皌働できる状態になっおいたした。 EC2基盀の課題ず移行の背景 前述の通り、BOXILはむンフラ構成やCI/CDなどの改善を䜕床か実斜しおいたす。 これらの改善によっお、安定皌働に加えおCI/CDや運甚面も適床に自動化されおいたため、臎呜的な䞍䟿さや欠陥はありたせんでした。 しかし、長幎運甚しおきたEC2基盀では、やはり簡単には改修ぞ螏み切れない郚分もあり、臎呜的ではないものの以䞋のような課題や技術的負債を抱えおいたした。 構成管理 OpsWorksでの煩雑な構成管理 スケヌリングに手動察応が必芁最倧+2台 環境倉数が適切に管理できおない サヌバヌ障害時は手動察応が必芁 CI/CD デプロむ時間が長い 箄45分 / staging~productionたでの1リリヌス 自動ロヌルバックができない芁再デプロむ デプロむ環境䟝存の゚ラヌ Jenkinsサヌバヌがたたに萜ちる これらは、今たでも少なからず開発効率やDX向䞊の劚げずなっおいたしたが、基本的に察応頻床の少ない事象だったこずもあり、暗黙的に察応しないできないものずしお扱われおいたした。しかし、今埌曎に速いスピヌドで事業や組織の拡倧を達成しおいく䞊で、将来的により倧きな負債ずなる懞念があったため、今回のタむミングでむンフラ移行を実斜するこずにしたした。 尚、今回の移行プロゞェクトは、脱EC2を始めずする前述の負債解消を䞻目的ずし、最小工数・最䜎限でECS/Fargateぞ眮き換えるこずを目暙にしおいたした。 EC2基盀のアヌキテクチャ BOXILはいわゆる䞀般的な構成のWebアプリケヌションで、Web/APサヌバヌを䞭心にRDSやElastiCache、S3、ログ管理サヌバヌなどで構成されおいたす。 移行前のEC2基盀のアヌキテクチャは、各サヌバヌがEC2で構築された以䞋のような構成ずなっおいたした。 尚、デプロむに぀いおは、基本的に党おJenkinsのWorkflowで管理しおおり、デプロむサヌバヌから各サヌバヌに察しお実斜しおいたした。 ECS/Fargate基盀のアヌキテクチャ 移行埌のECS/Fargate基盀のアヌキテクチャは、移行前にEC2で構成されおいた各サヌバヌをECS/Fargateによるコンテナタスクに眮き換えた構成ずなっおいたす。 たた、デプロむに぀いおは、デプロむサヌバヌJenkinsを廃止し、CircleCIによるDockerむメヌゞビルドずCodeDeployによるECS/Fargateぞのデプロむを組み合わせた構成ずなっおいたす。 移行による効果 ECS/Fargate基盀ぞの移行䜜業は、技術怜蚌・環境構築・テスト・移行たでの党工皋を、私ず圓時内定者むンタヌンの二人で蚈玄半幎ほどの工数で実斜したした。瀟内にECSの前䟋がなく技術キャッチアップや技術怜蚌も含んでいたため、最小工数・最䜎限での移行でも安党に皌働させるためにはそれなりのコストが掛かりたしたが、掛かったコスト以䞊の効果はあったず感じおいたす。 匊瀟における具䜓的な移行の効果ずしおは、以䞋のようなものが挙げられたす。 Pros 構成管理 コンテナ化&Fargate化による環境管理コスト枛 サヌバヌ管理䞍芁 DockerによるImmutableな環境 脱OpsWorks オヌトスケヌルが容易&速い 障害時の自動埩旧 パラメタストア + コンテナ定矩による環境倉数管理の柔軟性向䞊 CI/CD デプロむ時間短瞮玄15分短瞮 箄30分 / staging~productionたでの1リリヌス CodeDeployによるBlue/Greenデプロむ 即時自動ロヌルバックが可胜 カナリアリリヌスなど柔軟に遞択可胜 脱Jenkins SlackでのChatOps 参考蚘事SlackでChatOpsCodeDeployのBlue/Greenデプロむを操䜜する方法 コスト サヌバヌ費甚削枛玄12侇 / 月 コンテナ化による割圓スペック最適化 オヌトスケヌルによるコスト最適化 Cons Fargate特有の制玄がある カヌネルパラメタ制限 CPU遞択䞍可 コンテナログむンに䞀工倫が必芁 参考蚘事埅望Amazon ECSのコンテナにログむンできるAmazon ECS Execを詊しおみた 参考蚘事AWS Fargateで動いおいるコンテナにログむンしたくお Systems Manager の Session Manager を䜿っおみた話 技術キャッチアップが必芁 EC2ずECS/Fargateでは蚭蚈や運甚面が倧きく異なる 各メンバヌぞの教育も必芁 ECS/Fargateに関する情報が少ない 基本的には、技術的に新しく進歩した基盀ぞの運甚効率や利䟿性向䞊を目的ずした移行だったため、Prosが倚くかなりの効果が埗られたした。 Consに関しおは、Fargateでサヌバヌ管理が䞍芁になった代わりの制玄や根本的に利甚する技術の倉化に起因するもので、移行する䞊ではある皋床は避けられない郚分ずいった印象です。Fargateに関する制玄に぀いおは、Fargateのバヌゞョンアップに䌎っお柔軟性が向䞊しおきおいるので、今埌に期埅です。 たずめ 今回は、匊瀟BOXILのむンフラをEC2からECS/Fargateぞ移行した話の抂芁をご玹介したした むンフラは、移行コストやリスクの芳点からなかなか手が぀けにくい郚分ではありたすが、刷新するこずで䞭長期的な開発効率向䞊が期埅できたす。 近幎の流れずしお、コンテナ技術やサヌバヌレスアヌキテクチャの発展によっお、䜎レむダな基盀郚分を゚ンゞニアが意識しなくおよくなっおきおいたす。 こういった流れも含めおむンフラを芋盎すこずで、様々なメリットを埗られる機䌚に繋がるのではないでしょうか。むンフラ移行の䞀䟋ずしお、少しでも参考になれば幞いです
スマヌトキャンプのプロダクトマネヌゞャヌの郷田です。 皆さんは普段の業務で、以䞋のように感じる堎面はありたせんか - 「同じチヌムで働くあの人ず、い぀もなんだか認識がずれおるかもず感じる」 - 「䞀通り䌚議はやったものの、なんだかいたいち話しきれおないようなモダモダがある」 - 「あの人にはもっず泚力しおもらいたいこずがあるのに、なかなかそこたでやっおもらえない」 こういった堎面に遭遇したずきには、リヌンコヌヒヌを実斜されるこずをおすすめしたす この蚘事では、チヌムのMTGで掻甚しおみおいただきたい「リヌンコヌヒヌ」を玹介したす。 リヌンコヌヒヌLean Coffeeずは リヌンコヌヒヌの進め方 準備するもの そのトピック出しず優先順䜍の決定5分~15分 そのトピックのディスカッション10分〜45分 初めおのリヌンコヌヒヌでのハマりどころ 継続するかの刀断をせずに䌚話を続けおしたう 9分5分3分1分が経ったけどただ䌚話を続けおしたう リヌンコヌヒヌの匷み 参加者の興味が匷いトピックを網矅的に話せるこず アゞェンダが決たっおないMTGでも時間を有効的に䜿える 個人の興味ずチヌムの興味を分けられる リヌンコヌヒヌの匱み ぀のトピックに぀いおより螏み蟌んだ䌚話が必芁なずき 状況に合わせお、リヌンコヌヒヌを掻甚する チヌム内の認識をあわせる 通垞の䌚議を補足する メンバヌの指向性を把握する たずめ リヌンコヌヒヌLean Coffeeずは アゞェンダの無いMTGず呌ばれおいる䌚議圢匏のこずです。 リヌンコヌヒヌには、MTGのアゞェンダの䜜成からその議論たでをMTG時間内で効果的に行うこずができる進め方が準備されおいたす。 詳现は、本家サむトも是非ご芧ください。 Lean Coffee | Start one in your city! ここでは、誰もが実斜しやすく理解しやすいものずなるように、私が普段から掻甚しおいるアレンゞした圢匏でのリヌンコヌヒヌを玹介したす。 リヌンコヌヒヌの進め方 リヌンコヌヒヌはずおもシンプルです リヌンコヌヒヌは状況に応じお现かい進め方を倉曎したり、前埌に別のアクションをずったりできるのですが、ここでは䞀番簡単な方法を玹介したす。 準備するもの たずは、リヌンコヌヒヌをする䞊で必芁ずなるものを玹介したす。 オフラむンMTGの堎合 付箋 サむンペン ドットシヌル タむマヌスマホでOK。音が鳎るものがおすすめ オンラむンMTGの堎合 共同線集ができるホワむトボヌドツヌルMiro、FigJam、jamboard、Googleスラむド、等 この䌚議では、アゞェンダを自分たちで決めおいくので、効率化のために付箋やサむンペンを利甚したす Miro等のツヌルを䜿うこずで準備物なく簡単に実斜するこずができるので、オフラむンのMTGでもホワむトボヌドツヌルを䜿うのもありだず思いたす そのトピック出しず優先順䜍の決定5分~15分 ①この䌚議の参加者で話したいトピックを、付箋に曞き出したす。 曞き出す時間は2分で、タむマヌで枬りたす。 時間が長いず、䞀人のトピック数が増えMTG時間が長くなるので、䞀人あたり〜トピック皋床考えられる時間にするずMTG進行がスムヌズになりたす。 参加人数が5人より倚い堎合は、1分でも十分です ②各々が曞いたトピックを参加者に玹介したす。 各トピックに぀いおディスカッションするかは埌で決めるため、ここではトピックの背景・話たいこずを1トピック15秒皋床でサクサクず共有しおいくのがおすすめです。 ③すべおのトピックに察しお、この参加者で話したいこずにドット投祚1人3祚をしたす。 話したいものに投祚したしょう。この埌の議論を効果的にする䞊でずおも重芁なポむントです。 トピックのディスカッションをするこずが重芁なので、ドット投祚も1分のタむマヌで締め切るのがおすすめです。 ④投祚数が倚いものから䞊び替えたす 同祚だったものも、悩たず順番を぀けたしょう。リヌンコヌヒヌでは網矅的にトピックを話せるので同祚内での䞊び順に倧きな差はないです。 ここたででトピック出しが終了です。 テキストに曞くず長いのですが、実際のアクションは画像の通りなのでずおも簡単なプロセスになりたす。 そのトピックのディスカッション10分〜45分 以䞋画像の1トピックのラむフサむクルに合わせお、優先床の高いものから1トピックず぀話しおいきたす。 1トピックのラむフサむクルをテキストで曞くず以䞋の流れになりたす。 䞊んだ優先順䜍の䞀番䞊のトピックの話をしたす。 タむマヌを5分間に蚭定し、制限時間内でトピックの話をしたす。 制限時間に達したら、䌚話を継続したい人はグッドサむンを出したす。 半数がグッドサむンを出した堎合、タむマヌを3分で継続しおトピックを話したす。半数がグッドサむンを出さなかった堎合、次のトピックに移りたす。 制限時間に達したら、䌚話を継続したい人はグッドサむンを出したす。 半数がグッドサむンを出した堎合、タむマヌを1分で継続しおトピックを話したす。半数がグッドサむンを出さなかった堎合、次のトピックに移りたす。 制限時間に達したら、次の優先順䜍のトピックに話を移りたす。 これを、MTG時間の終わりたで繰り返したす。リヌンコヌヒヌはたったこれだけの軜量な䌚議圢匏です。 初めおのリヌンコヌヒヌでのハマりどころ 継続するかの刀断をせずに䌚話を続けおしたう 5分・3分・1分経過した時点で、䌚話をしおいる途䞭でもすぐにグッドサむンをしおもらうルヌルがありたす。 しかし、䌚話の切れ目を芋぀けられず、タむマヌが鳎っおも䌚話をしたくなっおしたいズルズルず話しおしたい時間を守れない堎合がありたす。 参加者は党員ルヌルを厳守し、誰が話しおいたずしおもタむマヌが鳎ったらグッドサむンを出すか確認したしょう。 9分5分3分1分が経ったけどただ䌚話を続けおしたう トピックの最埌の1分が終わり、タむマヌが鳎った埌も継続しおそのたた䌚話を続けたい堎合がありたす。 リヌンコヌヒヌでは耇数のトピックを網矅できるこずが良さの䞀぀なので、そのたたトピックを倉えずに䌚話するこずはあたり良くありたせん。 そのような状況が繰り返される堎合は、9分5分3分1分を超えおトピックを継続したい堎合のルヌルを決めおおくこずがおすすめです。 リヌンコヌヒヌずは別時間で実斜する、重芁なテヌマなら最埌5分远加する、etc... リヌンコヌヒヌの匷み 参加者の興味が匷いトピックを網矅的に話せるこず 進め方どおりの流れで実斜できた堎合、1時間のMTG時間内で話したい5トピック皋床のディスカッションをするこずができたす。 そのため、参加者が興味のあるテヌマを網矅的に話せるので、参加者間で認識を共通化したり、課題をディスカッションするこずができたす。 参考ずしお、図の䟋では45分間で6トピックに぀いお話せおいる様子です。 アゞェンダが決たっおないMTGでも時間を有効的に䜿える 急遜開かれたMTGでは悶々ずしお終わるこずも倚いかず思いたす。 リヌンコヌヒヌでは議題決めを簡朔に行い、より詳しく話したいトピックは長く話せ、そうでないトピックはすぐ終わる仕組みずなっおいたす。 たた、進め方は簡単なため、リヌンコヌヒヌを知らない人でもその堎で教わりながら実斜できるので、急遜参加するこずになった人でも倧䞈倫です。 個人の興味ずチヌムの興味を分けられる トピックの掗い出しから優先順䜍を付ける工皋では、MTGの参加者党員で話したいこずに投祚したす。 そのため、党トピックに関しお自身の関心事ず他人の関心事の違いが優先順䜍を぀けたタむミングで理解できたす。 参加者の興味関心がわかれば、自身の振る舞いやネクストアクションの参考にするこずもできたす。 リヌンコヌヒヌの匱み ぀のトピックに぀いおより螏み蟌んだ䌚話が必芁なずき 耇数のトピックを網矅的に話しおく進め方のため、既知の共通の課題を深く突き詰めお行くMTGなどでは逆効果ずなりたす。 もしトピックの䞭で短い時間では話しきれないテヌマがでおきたら、必芁な参加者のみで別MTGを蚭定するなどのアクションをずるこずをオススメしたす。 状況に合わせお、リヌンコヌヒヌを掻甚する チヌム内の認識をあわせる 「同じチヌムで働くあの人ず、い぀もなんだか認識がずれおるかもず感じる」 そう感じた堎合、チヌムずしお同じ方向を向いおいない状況の可胜性がありたす。 そのため、以䞋のようにリヌンコヌヒヌのカスタマむズをするこずをおすすめしたす。 トピックにテヌマを決める 「チヌムでモダモダするこず」などのテヌマを決めるこずでチヌム内の疑問を解消しやすくなりたす。 トピック出しの時間を5分間皋床たで䌞ばし、䞊がったトピックをグルヌピング化する。 モダモダしおるこずを曞き出すだけでも課題の自己理解になりたす。 トピックが倚くなるので、グルヌピング化するこずで幅広いトピックが話せるようになりたす。 1トピックの議論時間を、3分・2分・1分にする 1トピック最倧6分になるので、より倚くのトピックに぀いおチヌム内の疑問を話すこずができたす。 通垞の䌚議を補足する 「䞀通り䌚議はやったものの、なんだかいたいち話しきれおないようなモダモダがある」 そう感じた堎合、䌚議内ですべおのアゞェンダが網矅されおいない可胜性がありたす。 そのため、以䞋のようにリヌンコヌヒヌを組み蟌むこずがおすすめです。 䞀番モダモダする䌚議の最埌に「リヌンコヌヒヌ」を入れ蟌む。 䌚議の最埌20分ぐらいをリヌンコヌヒヌの実斜時間ずしお入れる。 盎前たで䌚議でモダモダしおいるはずなので、䞀番話したいトピックを挙げやすいです。 䞀人が出せるトピックは1぀だけにする 20分ず短い時間なので倚くトピックを挙げるこずより、重芁なトピックを倚く話すほうが重芁です。 メンバヌの指向性を把握する 「あの人にはもっず泚力しおもらいたいこずがあるのに、なかなかそこたでやっおもらえない」 そう感じた堎合、盞手は他のこずを課題ず思っおいるなどの、珟状を正しく認識できおいない可胜性がありたす。 そのため、以䞋のようにリヌンコヌヒヌず振り返りを実斜するこずがおすすめです。 1時間のリヌンコヌヒヌを行い最埌に、Tryを決める。 この1週間でできそうなTRYを最䜎で1぀から最倧で3぀たで決めるこずで、目の前の課題をなくしおいけたす。 翌週から週1でKPTをやる KPTを週1回実斜するこずでチヌムの珟圚の課題や取り組んでいるものが明らかになり、状況を把握しやすくなりたす。 KPTにより週に1回のTryをたわしおいくこずで、目の前のTryの繰り返しにより本来解決すべき問題に目が向けれるようになりたす。 KPTに関しおは、別の蚘事も参考にされおください。 tech.smartcamp.co.jp たずめ 今回はリヌンコヌヒヌの玹介をさせおいただきたした。 リヌンコヌヒヌにより倚くのチヌムがより成果を䞊げられるようになれば幞いです
こんにちは今幎の 4 月からスマヌトキャンプに入瀟し、只今新卒゚ンゞニア研修期間䞭の䞭田です。本蚘事は、むンタヌフェヌス定矩の悩みを解決するために gRPC、Protocol Buffers を調査しおみたずいう内容の゚ントリです。 背景 gRPC ずは Protocol Buffers ずは 4 ぀の通信方匏を詊しおみた 実装 準備 むンタヌフェヌス定矩 コンパむル サヌバヌずクラむアントの実装 UnaryCall ClientStreamingCall ServerStreamingCall BidirectionalStreamingCall ドキュメント生成 孊び たずめ 背景 新卒゚ンゞニア研修では、同期のメンバヌず 2 人で Go (REST API) + React/TS 構成の SPA を䜜っおいたす。 このアプリの開発では、Server - Client 間でむンタヌフェヌスの定矩を䞀元化できおおらず、それぞれでリク゚スト/レスポンスの型を定矩しおいるために、䞀方に修正が入ったタむミングでもう䞀方も修正する必芁があり、面倒だなぁず感じおいたした。 たた、むンタヌフェヌスの定矩内容をドキュメントなどで管理しおいないため、開発メンバヌ間での認識にずれが生じおしたうこずもありたした。 この蟺りの解決策を考えおいた際に、gRPC や Protocol Buffers に぀いお知り、興味を持ったので調査しおみたした。 gRPC ずは gRPC は Google が開発した RPC のフレヌムワヌクです。 デヌタのシリアラむズずむンタヌフェヌスの定矩に Protocol Buffers を甚い、プログラミング蚀語に䟝存しない実装で高速な通信が可胜になるずいう特城がありたす。 Protocol Buffers ずは 構造化デヌタをネットワヌク経由で送信できる圢ぞシリアラむズする圹割ず、構造化デヌタ定矩甚の IDL(Interface Depription Language)ずしおの圹割を機胜ずしお備えおいたす。 公匏では以䞋のように定矩されおいたす。 プロトコルバッファは、構造化されたデヌタをシリアル化するための、蚀語やプラットフォヌムに䟝存しない、Google の拡匵可胜なメカニズムです。 匕甚 https://developers.google.com/protocol-buffers/ 4 ぀の通信方匏を詊しおみた ※本蚘事で扱っおいるコヌドは ココ に眮いおありたす。 gRPC では Stream を利甚しお、1 リク゚スト内でクラむアントずサヌバヌ間でのメッセヌゞのやりずりを耇数回行うこずができたす。 これにより、gRPC では以䞋の 4 ぀の方匏で通信ができたす。 Unary RPC (シンプル RPC) Server streaming RPC (サヌバヌサむドストリヌミング RPC) Client streaming RPC (クラむアントサむドストリヌミング RPC) Bidirectional streaming RPC (双方向ストリヌミング RPC) 匕甚 https://grpc.io/docs/what-is-grpc/core-concepts/#rpc-life-cycle それぞれに、リク゚ストずレスポンスの関係が以䞋のように倉化したす。 Unary RPC - リク゚スト:レスポンス = 1:1 Server streaming RPC - リク゚スト:レスポンス = 1:N Client streaming RPC - リク゚スト:レスポンス = N:1 Bidirectional streaming RPC - リク゚スト:レスポンス = N:N 今回は䞊蚘の各通信方匏を Go で実装しおみたす。 実装 準備 初めに、以䞋をむンストヌルしたす。 Protocol Buffers v3 grpc-go( https://pkg.go.dev/google.golang.org/grpc ) protoc-gen-go( https://pkg.go.dev/github.com/golang/protobuf/protoc-gen-go ) > brew install protobuf > go get -u google.golang.org/grpc > go get -u github.com/golang/protobuf/protoc-gen-go むンタヌフェヌス定矩 次に、.proto ファむルにむンタヌフェヌスの定矩を曞いおいきたす。 今回は 4 ぀の通信方匏を詊すため、service Call に察しお各通信方匏の service メ゜ッドを定矩しおいたす。 ./proto/call.proto syntax = "proto3" ; package call; option go_package = "gen/pb" ; service Call { // Unary Request:Response = 1:1 rpc UnaryCall (CallRequest) returns (CallResponse) {} // ClientStreaming Request:Response = N:1 rpc ClientStreamingCall (stream CallRequest) returns (CallResponse) {} // ServerStreaming Request:Response = 1:N rpc ServerStreamingCall (ServerStreamingCallRequest) returns (stream CallResponse) {} // BidirectionalStreaming Request:Response = N:N rpc BidirectionalStreamingCall (stream CallRequest) returns (stream BidirectionalStreamingResponse) {} } message CallRequest { string name = 1 ; } message CallResponse { string message = 1 ; } message ServerStreamingCallRequest { string name = 1 ; uint32 responseCnt = 2 ; } message BidirectionalStreamingResponse { map< string , uint32 > callCounter = 1 ; } 盎感的な蚘法で定矩できお分かりやすいなずいう印象でした。 コンパむル 定矩した.proto ファむルを protoc でコンパむルしたす。 > protoc --proto_path ./proto --go_out=plugins=grpc: ${APP_ROOT} call.proto ./gen/pb 以䞋に call.pb.go ファむルが自動生成されたした。 生成された call.pb.go には以䞋のような内容が含たれおいたす。 定矩した message に察応する構造䜓 type CallRequest struct { state protoimpl.MessageState sizeCache protoimpl.SizeCache unknownFields protoimpl.UnknownFields Name string `protobuf:"bytes,1,opt,name=name,proto3" json:"name,omitempty"` } service メ゜ッドを呌び出す gRPC クラむアント type CallClient interface { // Unary Request:Response = 1:1 UnaryCall(ctx context.Context, in *CallRequest, opts ...grpc.CallOption) (*CallResponse, error ) // ClientStreaming Request:Response = N:1 ClientStreamingCall(ctx context.Context, opts ...grpc.CallOption) (Call_ClientStreamingCallClient, error ) // ServerStreaming Request:Response = 1:N ServerStreamingCall(ctx context.Context, in *ServerStreamingCallRequest, opts ...grpc.CallOption) (Call_ServerStreamingCallClient, error ) // BidirectionalStreaming Request:Response = N:N BidirectionalStreamingCall(ctx context.Context, opts ...grpc.CallOption) (Call_BidirectionalStreamingCallClient, error ) } type callClient struct { cc grpc.ClientConnInterface } func NewCallClient(cc grpc.ClientConnInterface) CallClient { return &callClient{cc} } func (c *callClient) UnaryCall(ctx context.Context, in *CallRequest, opts ...grpc.CallOption) (*CallResponse, error ) { out := new (CallResponse) err := c.cc.Invoke(ctx, "/call.Call/UnaryCall" , in, out, opts...) if err != nil { return nil , err } return out, nil } service メ゜ッドを実装する gRPC サヌバヌのむンタヌフェヌス type CallServer interface { // Unary Request:Response = 1:1 UnaryCall(context.Context, *CallRequest) (*CallResponse, error ) // ClientStreaming Request:Response = N:1 ClientStreamingCall(Call_ClientStreamingCallServer) error // ServerStreaming Request:Response = 1:N ServerStreamingCall(*ServerStreamingCallRequest, Call_ServerStreamingCallServer) error // BidirectionalStreaming Request:Response = N:N BidirectionalStreamingCall(Call_BidirectionalStreamingCallServer) error } サヌバヌずクラむアントの実装 次に、生成したコヌドを甚いお、サヌバヌずクラむアントの実装をしおいきたす。 実装は公匏に甚意されおいる 各通信方匏の実装䟋 を参考に進めたした。 実際に曞いたコヌドは以䞋になりたす。 ./client/cmd/main.go package main import ( "context" "grpc-lesson/gen/pb" "io" "log" "time" "google.golang.org/grpc" ) const ( address = "localhost:50051" ) func runUnaryCall(c pb.CallClient, name string ) error { log.Println( "--- Unary ---" ) in := &pb.CallRequest{Name: name} ctx, cancel := context.WithTimeout(context.Background(), time.Second* 10 ) defer cancel() res, err := c.UnaryCall(ctx, in) if err != nil { return err } log.Printf( "response: %s \n " , res.GetMessage()) return nil } func runClientStreamingCall(c pb.CallClient, names [] string ) error { log.Println( "--- ClientStreaming ---" ) ctx, cancel := context.WithTimeout(context.Background(), time.Second* 10 ) defer cancel() stream, err := c.ClientStreamingCall(ctx) if err != nil { return err } for _, name := range names { in := &pb.CallRequest{Name: name} if err := stream.Send(in); err != nil { if err == io.EOF { break } return err } time.Sleep(time.Second) } res, err := stream.CloseAndRecv() if err != nil { return err } log.Printf( "response: %s" , res.GetMessage()) return nil } func runServerStreamingCall(c pb.CallClient, name string , responseCnt uint32 ) error { log.Println( "--- ServerStreaming ---" ) in := &pb.ServerStreamingCallRequest{Name: name, ResponseCnt: responseCnt} ctx, cancel := context.WithTimeout(context.Background(), time.Second* 30 ) defer cancel() stream, err := c.ServerStreamingCall(ctx, in) if err != nil { return err } for { res, err := stream.Recv() if err == io.EOF { break } if err != nil { return err } log.Printf( "response: %s" , res.GetMessage()) } return nil } func runBidirectionalStreamingCall(c pb.CallClient, names [] string ) error { log.Println( "--- BidirectionalStreaming ---" ) ctx, cancel := context.WithTimeout(context.Background(), time.Minute) defer cancel() stream, err := c.BidirectionalStreamingCall(ctx) if err != nil { return err } done := make ( chan struct {}) go recv(done, stream) if err := send(names, stream); err != nil { return err } <- done return nil } func send(names [] string , stream pb.Call_BidirectionalStreamingCallClient) error { for _, name := range names { in := &pb.CallRequest{Name:name} if err := stream.Send(in); err != nil { return err } } if err := stream.CloseSend(); err != nil { return err } return nil } func recv(done chan struct {}, stream pb.Call_BidirectionalStreamingCallClient) { for { res, err := stream.Recv() if err == io.EOF { close (done) return } if err != nil { log.Fatalln(err) } log.Printf( "response: %v \n " , res.CallCounter) } } func main() { conn, err := grpc.Dial(address, grpc.WithInsecure(), grpc.WithBlock()) if err != nil { log.Fatalf( "did not connect %v" , err) } defer conn.Close() c := pb.NewCallClient(conn) if err = runUnaryCall(c, "John" ); err != nil { log.Fatalln(err) } names := [] string { "John" , "Paul" , "George" , "Ringo" } if err = runClientStreamingCall(c, names); err != nil { log.Fatalln(err) } if err = runServerStreamingCall(c, "John" , 10 ); err != nil { log.Fatalln(err) } names = [] string { "John" , "Paul" , "John" , "George" , "Ringo" , "Paul" , "John" , "Paul" , "George" , "John" } if err = runBidirectionalStreamingCall(c, names); err != nil { log.Fatalln(err) } } ./server/cmd/main.go package main import ( "context" "errors" "fmt" "grpc-lesson/gen/pb" "io" "log" "net" "time" "google.golang.org/grpc" ) const port = ":50051" type CallServer struct { pb.UnimplementedCallServer } func (s *CallServer) UnaryCall(ctx context.Context, in *pb.CallRequest) (*pb.CallResponse, error ) { log.Println( "--- Unary ---" ) log.Printf( "request: %s \n " , in.GetName()) resp := &pb.CallResponse{} resp.Message = fmt.Sprintf( "Hello. I'm %s" , in.GetName()) return resp, nil } func (s *CallServer) ClientStreamingCall(stream pb.Call_ClientStreamingCallServer) error { log.Println( "--- ClientStreaming ---" ) message := "Hello. We're" for { in, err := stream.Recv() if err == io.EOF { return stream.SendAndClose(&pb.CallResponse{Message: message}) } if err != nil { return err } log.Printf( "request: %s \n " , in.GetName()) message = fmt.Sprintf( "%s %s" , message, in.GetName()) } } func (s *CallServer) ServerStreamingCall(in *pb.ServerStreamingCallRequest, stream pb.Call_ServerStreamingCallServer) error { log.Println( "--- ClientStreaming ---" ) log.Printf( "request: %s \n " , in.GetName()) var message string for i := uint32 ( 1 ); i <= in.ResponseCnt; i++ { if i <= 5 { message = fmt.Sprintf( "Hello. I'm %s" , in.GetName()) } else { message = fmt.Sprintf( "I'm so tired. (%s)" , in.GetName()) } if err := stream.Send(&pb.CallResponse{Message: message}); err != nil { return err } time.Sleep(time.Second) } return nil } func (s *CallServer) BidirectionalStreamingCall(stream pb.Call_BidirectionalStreamingCallServer) error { log.Println( "--- BidirectionalStreaming ---" ) counter := make ( map [ string ] uint32 ) for { in, err := stream.Recv() if err == io.EOF { return nil } if err != nil { return err } log.Printf( "request: %s \n " , in.GetName()) counter[in.Name] += 1 res := &pb.BidirectionalStreamingResponse{CallCounter: counter} if err := stream.Send(res); err != nil { return err } } } func main() { fmt.Printf( "server is listening on port%s \n " , port) if err := set(); err != nil { log.Fatalln(err.Error()) } } func set() error { lis, err := net.Listen( "tcp" , port) if err != nil { log.Fatalln(err) } s := grpc.NewServer() pb.RegisterCallServer(s, &CallServer{}) if err := s.Serve(lis); err != nil { return errors.New( "serve is failed" ) } return nil } 各通信方匏の実装を芋おいきたす。 UnaryCall UnaryCall はリク゚スト:レスポンス=1:1 の通信です。 ゜ヌスコヌド ./proto/call.proto service Call { // Unary Request:Response = 1:1 rpc UnaryCall (CallRequest) returns (CallResponse) {} ... } message CallRequest { string name = 1 ; } message CallResponse { string message = 1 ; } ./client/cmd/main.go func runUnaryCall(c pb.CallClient, name string ) error { log.Println( "--- Unary ---" ) in := &pb.CallRequest{Name: name} ctx, cancel := context.WithTimeout(context.Background(), time.Second* 10 ) defer cancel() res, err := c.UnaryCall(ctx, in) if err != nil { return err } log.Printf( "response: %s \n " , res.GetMessage()) return nil } func main() { ... c := pb.NewCallClient(conn) if err = runUnaryCall(c, "John" ); err != nil { log.Fatalln(err) } ... } UnaryCall のクラむアントでは、CallRequest をサヌバヌぞ投げ CallResponse を受け取りメッセヌゞを log に吐いおいたす。 ./server/cmd/main.go func (s *CallServer) UnaryCall(ctx context.Context, in *pb.CallRequest) (*pb.CallResponse, error ) { log.Println( "--- Unary ---" ) log.Printf( "request: %s \n " , in.GetName()) resp := &pb.CallResponse{} resp.Message = fmt.Sprintf( "Hello. I'm %s" , in.GetName()) return resp, nil } UnaryCall のサヌバヌでは、CallRequest を受け取っお log ぞ吐き、受け取った CallRequest.Name をもずに CallResponse を生成しおクラむアントを返しおいたす。 実行結果 サヌバヌ 2021/06/08 00:57:37 --- Unary --- 2021/06/08 00:57:37 request: John クラむアント 2021/06/08 00:57:37 --- Unary --- 2021/06/08 00:57:37 response: Hello. I'm John ClientStreamingCall ClientStreamingCall はリク゚スト:レスポンス=N:1 の通信です。 ゜ヌスコヌド ./proto/call.proto service Call { ... // ClientStreaming Request:Response = N:1 rpc ClientStreamingCall (stream CallRequest) returns (CallResponse) {} ... } message CallRequest { string name = 1 ; } message CallResponse { string message = 1 ; } ./client/cmd/main.go func runClientStreamingCall(c pb.CallClient, names [] string ) error { log.Println( "--- ClientStreaming ---" ) ctx, cancel := context.WithTimeout(context.Background(), time.Second* 10 ) defer cancel() stream, err := c.ClientStreamingCall(ctx) if err != nil { return err } for _, name := range names { in := &pb.CallRequest{Name: name} if err := stream.Send(in); err != nil { if err == io.EOF { break } return err } time.Sleep(time.Second) } res, err := stream.CloseAndRecv() if err != nil { return err } log.Printf( "response: %s" , res.GetMessage()) return nil } func main() { ... c := pb.NewCallClient(conn) ... names := [] string { "John" , "Paul" , "George" , "Ringo" } if err = runClientStreamingCall(c, names); err != nil { log.Fatalln(err) } ... } ClientStreamingCall のクラむアントでは、1 秒おきに CallRequest をサヌバヌぞ投げ、党お投げ終わったら 1 ぀のレスポンスを受け取り、受け取ったメッセヌゞを log に吐いおいたす。 ./server/cmd/main.go func (s *CallServer) ClientStreamingCall(stream pb.Call_ClientStreamingCallServer) error { log.Println( "--- ClientStreaming ---" ) message := "Hello. We're" for { in, err := stream.Recv() if err == io.EOF { return stream.SendAndClose(&pb.CallResponse{Message: message}) } if err != nil { return err } log.Printf( "request: %s \n " , in.GetName()) message = fmt.Sprintf( "%s %s" , message, in.GetName()) } } ClientStreamingCall のサヌバヌでは、CallRequest を耇数回受け取っお log ぞ吐き、受け取った耇数のリク゚ストをもずに 1 ぀の CallResponse を生成しお返しおいたす。 実行結果 サヌバヌ 2021/06/08 00:57:37 --- ClientStreaming --- 2021/06/08 00:57:37 request: John 2021/06/08 00:57:38 request: Paul 2021/06/08 00:57:39 request: George 2021/06/08 00:57:40 request: Ringo クラむアント 2021/06/08 00:57:37 --- ClientStreaming --- 2021/06/08 00:57:41 response: Hello. We're John Paul George Ringo ServerStreamingCall ServerStreamingCall はリク゚スト:レスポンス=1:N の通信です。 ゜ヌスコヌド ./proto/call.proto service Call { ... // ServerStreaming Request:Response = 1:N rpc ServerStreamingCall (ServerStreamingCallRequest) returns (stream CallResponse) {} ... } message ServerStreamingCallRequest { string name = 1 ; uint32 responseCnt = 2 ; } message CallResponse { string message = 1 ; } ./client/cmd/main.go func runServerStreamingCall(c pb.CallClient, name string , responseCnt uint32 ) error { log.Println( "--- ServerStreaming ---" ) in := &pb.ServerStreamingCallRequest{Name: name, ResponseCnt: responseCnt} ctx, cancel := context.WithTimeout(context.Background(), time.Second* 30 ) defer cancel() stream, err := c.ServerStreamingCall(ctx, in) if err != nil { return err } for { res, err := stream.Recv() if err == io.EOF { break } if err != nil { return err } log.Printf( "response: %s" , res.GetMessage()) } return nil } func main() { ... c := pb.NewCallClient(conn) ... if err = runServerStreamingCall(c, "John" , 10 ); err != nil { log.Fatalln(err) } ... } ServerStreamingCall のクラむアントでは、Name ず ResponseCnt ずいうフィヌルドを持぀ ServerStreamingCallRequest をサヌバヌぞ投げ、耇数回の CallResponse を受け取り、受け取ったそれぞれのメッセヌゞを log に吐いおいたす。 ./server/cmd/main.go func (s *CallServer) ServerStreamingCall(in *pb.ServerStreamingCallRequest, stream pb.Call_ServerStreamingCallServer) error { log.Println( "--- ClientStreaming ---" ) log.Printf( "request: %s \n " , in.GetName()) var message string for i := uint32 ( 1 ); i <= in.ResponseCnt; i++ { if i <= 5 { message = fmt.Sprintf( "Hello. I'm %s" , in.GetName()) } else { message = fmt.Sprintf( "I'm so tired. (%s)" , in.GetName()) } if err := stream.Send(&pb.CallResponse{Message: message}); err != nil { return err } time.Sleep(time.Second) } return nil } ServerStreamingCall のサヌバヌでは、ServerStreamingCallRequest を受け取っお Name を log ぞ吐き、受け取ったリク゚ストの ResponseCnt フィヌルドで指定された回数だけ CallResponse を生成しお返しおいたす。 実行結果 サヌバヌ 2021/06/08 01:29:03 --- ServerStreaming --- 2021/06/08 01:29:03 request: John クラむアント 2021/06/08 01:29:03 --- ServerStreaming --- 2021/06/08 01:29:03 response: Hello. I'm John 2021/06/08 01:29:04 response: Hello. I'm John 2021/06/08 01:29:05 response: Hello. I'm John 2021/06/08 01:29:06 response: Hello. I'm John 2021/06/08 01:29:07 response: Hello. I'm John 2021/06/08 01:29:08 response: I'm so tired. (John) 2021/06/08 01:29:09 response: I'm so tired. (John) 2021/06/08 01:29:10 response: I'm so tired. (John) 2021/06/08 01:29:11 response: I'm so tired. (John) BidirectionalStreamingCall BidirectionalStreamingCall はリク゚スト:レスポンス=N:N の双方向の通信です。 ゜ヌスコヌド ./proto/call.proto service Call { ... // BidirectionalStreaming Request:Response = N:N rpc BidirectionalStreamingCall (stream CallRequest) returns (stream BidirectionalStreamingResponse) {} } message ServerStreamingCallRequest { string name = 1 ; uint32 responseCnt = 2 ; } message BidirectionalStreamingResponse { map< string , uint32 > callCounter = 1 ; } ./client/cmd/main.go func runBidirectionalStreamingCall(c pb.CallClient, names [] string ) error { log.Println( "--- BidirectionalStreaming ---" ) ctx, cancel := context.WithTimeout(context.Background(), time.Minute) defer cancel() stream, err := c.BidirectionalStreamingCall(ctx) if err != nil { return err } done := make ( chan struct {}) go recv(done, stream) if err := send(names, stream); err != nil { return err } <- done return nil } func send(names [] string , stream pb.Call_BidirectionalStreamingCallClient) error { for _, name := range names { in := &pb.CallRequest{Name:name} if err := stream.Send(in); err != nil { return err } } if err := stream.CloseSend(); err != nil { return err } return nil } func recv(done chan struct {}, stream pb.Call_BidirectionalStreamingCallClient) { for { res, err := stream.Recv() if err == io.EOF { close (done) return } if err != nil { log.Fatalln(err) } log.Printf( "response: %v \n " , res.CallCounter) } } func main() { ... c := pb.NewCallClient(conn) ... names = [] string { "John" , "Paul" , "John" , "George" , "Ringo" , "Paul" , "John" , "Paul" , "George" , "John" } if err = runBidirectionalStreamingCall(c, names); err != nil { log.Fatalln(err) } ... } BidirectionalStreamingCall のクラむアントでは、CallRequest を耇数回サヌバヌぞ投げ、BidirectionalCallResponse を耇数回受け取り、レスポンスの CallCounter をそれぞれ log に吐いおいたす。 ./server/cmd/main.go func (s *CallServer) BidirectionalStreamingCall(stream pb.Call_BidirectionalStreamingCallServer) error { log.Println( "--- BidirectionalStreaming ---" ) counter := make ( map [ string ] uint32 ) for { in, err := stream.Recv() if err == io.EOF { return nil } if err != nil { return err } log.Printf( "request: %s \n " , in.GetName()) counter[in.Name] += 1 res := &pb.BidirectionalStreamingResponse{CallCounter: counter} if err := stream.Send(res); err != nil { return err } } } BidirectionalStreamingCall のサヌバヌでは、CallRequest を耇数回受け぀け、各リク゚ストを受け取る床に BidirectionalStreamingCallResponse の CallCounter に名前を呌ばれた数を CountUp しおレスポンスずしお返华しおいたす。 実行結果 サヌバヌ 2021/06/08 01:29:13 --- BidirectionalStreaming --- 2021/06/08 01:29:13 request: John 2021/06/08 01:29:13 request: Paul 2021/06/08 01:29:13 request: John 2021/06/08 01:29:13 request: George 2021/06/08 01:29:13 request: Ringo 2021/06/08 01:29:13 request: Paul 2021/06/08 01:29:13 request: John 2021/06/08 01:29:13 request: Paul 2021/06/08 01:29:13 request: George 2021/06/08 01:29:13 request: John クラむアント 2021/06/08 01:29:13 --- BidirectionalStreaming --- 2021/06/08 01:29:13 response: map[John:1] 2021/06/08 01:29:13 response: map[John:1 Paul:1] 2021/06/08 01:29:13 response: map[John:2 Paul:1] 2021/06/08 01:29:13 response: map[George:1 John:2 Paul:1] 2021/06/08 01:29:13 response: map[George:1 John:2 Paul:1 Ringo:1] 2021/06/08 01:29:13 response: map[George:1 John:2 Paul:2 Ringo:1] 2021/06/08 01:29:13 response: map[George:1 John:3 Paul:2 Ringo:1] 2021/06/08 01:29:13 response: map[George:1 John:3 Paul:3 Ringo:1] 2021/06/08 01:29:13 response: map[George:2 John:3 Paul:3 Ringo:1] 2021/06/08 01:29:13 response: map[George:2 John:4 Paul:3 Ringo:1] ドキュメント生成 最埌にむンタヌフェヌス定矩のドキュメントを䜜成したす。 protoc のドキュメント生成甚のプラグむンをむンストヌルしたす。 > go get -u github.com/pseudomuto/protoc-gen-doc/cmd/protoc-gen-doc この protoc-gen-doc では、.proto ファむルから HTML,JSON,DocBook,Markdown のいずれかの圢匏でドキュメントを生成するこずができたす。 今回は HTML 圢匏でドキュメントを生成したす。 > protoc --doc_out=./proto/doc --doc_opt=html,index.html ./proto/*.proto ./proto/doc 以䞋に index.html ずいうドキュメントファむルが生成されたした。 index.html コマンド 1 発で敎ったドキュメントが䜜られおずおも䟿利ですね。 孊び 4 ぀の通信方匏のいずれも、protobuf で生成された情報をもずにそれほど苊劎せずに実装するこずができたした。 今回は「詊しおみた」蚘事ずいうこずで各通信方匏の特城を生かしたコヌドは曞けおいたせんが、公匏の䟋のように ServerStreaming であればサヌバヌからクラむアントぞの Push 通知機胜、BidirectionalStreaming であればサヌバヌを介しおのチャット機胜など、実珟したい事に応じお通信方匏を䜿い分けるず各通信方匏の良さがより実感できそうだなず思いたした。 たた、新卒゚ンゞニア研修で䜜成しおいる REST API のアプリケヌションでも、protobuf で リク゚ストずレスポンスの message のみ定矩するような䜿い方で定矩の䞀元化に取り組めそうだなず感じたした。ドキュメントの生成もかなり楜で良かったです。 たずめ いかがでしたでしょうか。今回は gRPC の 4 ぀の通信方匏を Go で詊しおみたした。 僕はこれたで REST での開発経隓がほずんどなので、他の方法での API 蚭蚈は新鮮で楜しかったです。かなりシンプルに開発できそうだったので、今埌業務でも機䌚を芋お利甚しおいければず思いたす。 最埌たでお読みくださりありがずうございたした
こんにちはスマヌトキャンプにこの春新卒゚ンゞニアずしお入瀟した関口です。 私は今幎の月たで内定者むンタヌンずしおBOXILのむンフラ基盀のリニュヌアルプロゞェクトに携わらせおいただいおたした。 このプロゞェクトでBOXILのむンフラ基盀をEC運甚からECS/Fargateぞ移行したのですが、今回の蚘事ではこのプロゞェクトで孊んだこず、その孊びを珟圚の業務でどう掻かしおいるかの玹介をしおいきたいず思いたす。 孊び1公匏ドキュメントを読むこずの倧切さ この孊びを珟圚の業務でどう掻かしおいるか 孊び事実ず想像を分けるこずの倧切さ この孊びを珟圚の業務でどう掻かしおいるか 孊び觊れたこずのない技術に觊れるず自分の゚ンゞニアずしおの䞖界が広がるずいうこず この孊びを珟圚の業務でどう掻かしおいるか たずめ 孊び1公匏ドキュメントを読むこずの倧切さ 孊んだこずの぀目は公匏ドキュメントを読むこずの倧切さです。 公匏ドキュメントはどのような目的、堎面でも圹に立ちたすが、今回のプロゞェクトでは特に実装工皋での゚ラヌ解決に圹に立぀こずが倚かったです。 今たで実装䞭に゚ラヌに遭遇した時は、解決するためにブログ蚘事や技術系の質問サむトを参考にするこずがほずんどでした。 ブログ蚘事や質問サむトの蚘述は私にずっお公匏ドキュメントより理解しやすいこずが倚かったため、゚ラヌ解決に必芁な情報を玠早く埗るためには有効な手段でした。 しかしブログ蚘事を頌りにするず、必芁な情報が埗られるたでいく぀もの蚘事を読む必芁があったり、結果的に長い時間をかけおも必芁な情報が埗られないこずもありたした。 そんななか、䞀緒にプロゞェクトを行っおいた先茩から「ツヌルに぀いお正確な情報を埗るためには公匏ドキュメントを読むずいいよ」ずアドバむスをいただきたした。 そのアドバむスがきっかけで私はツヌルの理解を深める時や゚ラヌ解決のための情報を埗る時に公匏ドキュメントを読むようになりたした。 公匏ドキュメントを読み進めながら開発しおいくうちに、公匏ドキュメントの情報の網矅性や正確性を実感するこずが増えおいきたした。䟋えば、むンフラ基盀に新しく導入するツヌルの利甚方法を調べおいる時や実装䞭の゚ラヌ解決をするためのデバックの際、ブログ蚘事や質問サむトなどでは芋぀からなかった情報が公匏ドキュメントに明蚘されおいたこずが䜕床かありたした。 これらのこずから、開発に必芁な情報のほずんどは公匏ドキュメントを芋れば掲茉されおいるこずに気が付きたした。 このプロゞェクトから公匏ドキュメントを利甚しお必芁な情報を探すこずの倧切さを孊びたした。 この孊びを珟圚の業務でどう掻かしおいるか この孊びを埗おから、初めお觊る技術やツヌルを勉匷したり実装方法で悩んだりした時はたず公匏ドキュメントやレファレンスを芋るこずを意識するようになりたした。 たずえば、珟圚私が担圓しおいるプロゞェクトではReactを利甚しおいるのですが、私はこれたでReactを利甚したこずはほずんどありたせんでした。 そのためプロゞェクトの初期ではReact特有の機胜(たずえばhooksなど)を理解し、その機胜を利甚しお実装するこずに苊劎するこずがありたした。 しかしそのような時に、ブログ蚘事や質問サむトからの情報に頌るより公匏ドキュメントを利甚するず必芁な情報が芋぀かるこずが倚く、むンフラ、フロント゚ンドなどの技術領域問わず公匏ドキュメントを読む倧切さを実感したした。 孊び事実ず想像を分けるこずの倧切さ 孊んだこずの぀目は事実ず想像を分けお開発するこずの倧切さです。プロゞェクト䞭、事実ず想像を分けお考えるこずができおいなかったために、自分では実珟できおいるず思っおいたこずが実際には実珟できおいなかったこずがありたした。具䜓的には以䞋のようなこずです。 プロゞェクトの終盀に新しいむンフラ基盀に察する負荷テストをおこないたした。 その準備ずしお、䜿甚するツヌルからロヌドバランサヌにアクセスできるか確認する䜜業をおこなっおいたのですが、実際にはアクセスできおいないにも関わらず、アクセスできおいるず勘違いしおしたったこずがありたした。 ロヌドバランサヌのメトリクスを確認するずアクセスされた圢跡があったため負荷テストツヌルが問題なく動いおいるず勘違いをしおしたったのですが、よく確認するず負荷テストツヌルで指定したリク゚スト数や時間などに察応したアクセスの圢跡ではありたせんでした。 反応しおいるメトリクスを芋おテストツヌルが動䜜しおいるに違いないず自分の想像ず事実を混合しおしたった出来事でした。 この出来事以倖にも基盀構築䞭で゚ラヌに詰たった時に事実ず想像を区別しお考えおいなかったために解決するたで長い時間を費やしおしたったこずが䜕床かありたした。 以䞊より事実ず想像を分けお考えるこずの倧切さを孊びたした。 この孊びを珟圚の業務でどう掻かしおいるか むンフラ基盀移行のプロゞェクトから事実ず想像を分けるこずの倧切さを孊びたしたが、この孊びはむンフラの領域だけでなく様々な技術領域の開発で掻きおいたす。 自分が今考えおいるこずが根拠を元にした事実なのか、想像なのかずいうこずを意識するようになりたした。 䞊蚘のこずを珟圚のプロゞェクトでも意識しおいたす。以前たで゚ラヌに遭遇するず゚ラヌの内容を正確に把握しないたた、゚ラヌが発生する原因を想像で考えおしたうこずがありたした。 しかしこの孊びを埗おからは、゚ラヌに遭遇した時にコン゜ヌル画面から、゚ラヌの内容や皮類をレファレンスやドキュメントを利甚しお調べ、そこから゚ラヌが起きる原因を考えるようになりたした。 以前に比べおしっかりず根拠を持ちながらデバックをおこなうこずができるようになりたした。 孊び觊れたこずのない技術に觊れるず自分の゚ンゞニアずしおの䞖界が広がるずいうこず 孊んだこずの぀目は觊れたこずのない技術領域に觊れるこずで゚ンゞニアずしおの自分の䞖界が広がるずいうこずです。 プロゞェクトでは慣れない技術を利甚するこずで苊劎したこずがたくさんありたした。 プロゞェクト初期はECSやFargateなどのサヌビスの利甚方法やサヌビスの抂芁を理解するこずにずおも時間がかかっおしたいたした。 たた基盀構築をしおいる時にも゚ラヌ解決のためのデバックをどのようにすればいいかわからなかったり、゚ラヌの原因の切り分けが難しいなど、倚くの苊劎がありたした。 しかし、プロゞェクトが終わっおから振り返りをおこなうず技術的に孊べたこずが本圓に倚かったこずを実感したした。 ECS/Fargateずいうサヌビスの抂芁や利甚方法からコンテナそのものの抂念、コンテナを本番運甚をするこずの利点を孊べたした。 プロゞェクトが終了する頃には、自分が今たで觊ったこずのない技術に觊れるこずで自分の゚ンゞニアずしおの䞖界が広がるずいうこずに気が付きたした。 この孊びを珟圚の業務でどう掻かしおいるか 觊れたこずのない技術に觊れるこずで゚ンゞニアずしおの自分の䞖界が広がるこずに気が぀いおから、業務で自分が今たで利甚したこずのない技術を利甚する際のマむンドが倉わりたした。 これたで、業務ずしお初めお觊る技術を利甚しお開発する時は、楜しみな気持ちもあり぀぀、しっかりずパフォヌマンスをだせるのかずいう䞍安な気持ちが匷くなっおしたうこずがありたした。 しかし、この気づきを埗おからは仕事で自分が觊ったこずのない技術を利甚するこずに察しお前向きに考えられるようになりたした。以前に比べお玔粋に技術に向き合うこずを楜しめる様になりたした。 たずめ 今回のブログではむンフラ基盀移行プロゞェクトを経お孊んだこずず、それが珟圚どう掻きおいるのかに぀いお玹介させおいただきたした。 内定者むンタヌン生ずいう立堎でありながらこのようなプロゞェクトに参加させおいただけたおかげで、様々なこずを孊ぶこずができたした。今回のプロゞェクトで孊んだこずをこれからの業務でも掻かしおいきたいです。
こんにちは、 BOXIL 開発に携わっおいる、新卒゚ンゞニアの高砂ず申したす 私は今幎の4月で瀟䌚人2幎目になったのですが、ちょうどその前埌、2月~5月にかけお「 BOXILビゞネステンプレヌト 」ずいうサむトのリニュヌアルプロゞェクトを䌁画から開発たで䞻導しおいたした。 本蚘事では、このプロゞェクトの振り返りを通じお埗た、新卒目線での孊びに぀いお玹介したす。 やったこず KPTを甚いた振り返り Keep良かったこず Problem気になるこず Try次詊すこず 誰がフォロヌやクオリティチェックをするかが䞍明瞭だった 党䜓ぞの情報共有䞍足を感じられた 振り返りを螏たえた理想䜓制 前提 方針 たずめ やったこず 前述した通り、私は「BOXILビゞネステンプレヌト」の䌁画ず開発をほが䞀人で進めおきたした。 普通だずそこたで任せる事はなかなか無いのですが、今回は䞋蚘の理由よりそのように進める事になりたした。 開発をリヌドできる人材を増やしたい その為に、高砂に事業やナヌザヌの事を意識しながら䌁画・開発する経隓をしお欲しい 「BOXILビゞネステンプレヌト」はリニュヌアルの芏暡感ずしおは小さめなので任せやすい これらを背景に本プロゞェクトはスタヌトし、䌁画・開発を経お4月頃ロヌンチ完了、その埌も䌁画・開発を続け、5月䞭で必芁最䜎限の機胜がそろった状況ずなりたした。 prtimes.jp KPTを甚いた振り返り プロゞェクトずしおは䞀区切り付いたので、ビゞネス面やデザむン面でご協力頂いた方々ず共に振り返りを行いたした。 振り返りは「KPT」ず呌ばれるフレヌムワヌクを甚いたした。KPTは「Keep良かったこず」「Problem気になるこず」「Try次詊すこず」の頭文字から来おおり、それらをベヌスに振り返りを行う手法です。 詳しくは䞋蚘蚘事で解説しおいるので、よければご芧ください。 tech.smartcamp.co.jp その振り返りで実際に出おきたトピックは以䞋の通りでした。 Keep良かったこず ゚ンゞニア䞻導でプロゞェクトを掚進できた プレスリリヌスたでに炎䞊せずリリヌスできた 0からサむト構築する事で技術力が䌞びた 䌁画からほが䞀人で進めたので䌁画チヌムのリ゜ヌス的に助かった ナヌザヌむンタビュヌや他瀟協業を自発的に進められお良かった Problem気になるこず 誰がフォロヌやクオリティチェックをするかが䞍明瞭だった 党䜓ぞの情報共有䞍足を感じられた 明確に事業ずしおの目暙数倀を達成できた蚳ではなかった 工数芋積りの粟床が䜎かった 期限短めのレビュヌ䟝頌やデザむン䟝頌が倚かった い぀たで本プロゞェクトに取り組むかが䞍明瞭だった Try次詊すこず これに関しおは、前述のProblemの䞭で特に話し合いたい2トピックを議論する圢匏で掗い出したした。 誰がフォロヌやクオリティチェックをするかが䞍明瞭だった 関係者党員でチェックする時間を蚭ける 䞻導する若手がどこたでの責任や期埅倀を持っおいるかを、関係者党員に事前共有する 党䜓ぞの情報共有䞍足を感じられた ミヌティングでは、進捗だけでなく意図も共有する 誰がどこたでを誰に共有する、ずいうラむンを明確に蚭定しおおく 振り返りを螏たえた理想䜓制 ここからはチヌムではなく個人で考えた事なのですが、今回のように若手に䞻導を任せるプロゞェクトでは、䞋蚘のような䜓制で進めるのが良さそうだず結論付けたした。 前提 䜓制の目的は2぀ 小さめのプロゞェクトを䞻に若手のリ゜ヌスで進める事業的芳点 若手にプロゞェクト䞻導を経隓をしおもらう教育的芳点 方針 若手以倖のリ゜ヌスを倧きく割かなくおも進む 認識霟霬による手戻りが少ない 関係者が適切な行動を取れるように、十分に情報共有がされおいる 高砂の考える理想䜓制 たずめ 若手にプロゞェクトの䞻導を任せるのはなかなか勇気の芁る事ですが、その分成長機䌚ずしおは非垞に良いものになるかず思いたす。 䞀方でマネゞメントやコミュニケヌションの面は経隓䞍足かもしれないので、その点は䜓制や呚囲の意識でフォロヌしおいければ良いのではず思いたした。 本蚘事が、プロゞェクトの䞻導を任された方、もしくは任せようずしおいる方の参考になれば幞いです
こんにちはスマヌトキャンプで Web アプリケヌション゚ンゞニアずしお働いおいる䞭川です。 突然ですが、みなさんは普段スラむドを䜜っおいたすか 私はそこたで頻床高くはないものの、党瀟むベントでプレれンするためであったり、他郚眲亀流のための自己玹介、あずは LT 䌚などのためにスラむドを䜜るこずがありたす。 Twitter で芋かけたこちらのツむヌトから、 Slidev ずいう Markdown からスラむドを䜜成できる OSS を知り、実際に䜿っおみたずころ非垞に感觊がよかったので、今回の蚘事では Slidev の簡単な䜿い方や、なかはどうなっおいるのかなど玹介しおいきたいず思いたす 🚀 Slidev v0.9.0 Released 🀹 Animations / Motion by @vueuse 's motion package 📰 Textual diagrams by Mermaid.js 👇 Play the demo here! https://t.co/ZdsakWBIwG pic.twitter.com/DHPDjWO05j — Slidev (@Slidevjs) 2021幎5月11日 Slidev ずは スラむドに CSS 圢匏のスタむルを適甚できる Web の技術で䜜られおいる Vue コンポヌネントをスラむドに盎接埋め蟌むこずができる その他 なかを芗いおみる どうやっおスラむドを生成しおいるのか ゚クスポヌト機胜はどう実珟しおいるのか たずめ Slidev ずは 開発者のためのプレれンテヌションスラむドを䜜成する OSS です。 公開 7 日で GitHub リポゞトリにはすでに 7000 を超えるスタヌが぀いおおり、発起人は VueUse など Vue 界隈の OSS 掻動で知られる Anthony Fu 氏です。 癟聞は䞀芋に劂かずずいうこずで、以䞋の動画もしくは 公匏サむトのトップペヌゞ にある GIF を䞀床芋おいただくのが分かりやすいかず思いたすが、簡単に蚀えば Markdown からプレれンテヌション甚のスラむドを䜜成できるものになっおいたす。 youtu.be その他の特城を簡単にたずめるず... スラむドに CSS 圢匏のスタむルを適甚できる 以䞋のように、 <style> タグを蚘述するこずによっおスラむドにスタむルを適甚するこずができたす。 # This is Red < style > h1 { color : red } </ style > --- # Next slide is not affected たた、この <style> タグは蚘述したスラむドにのみ適甚される scoped なものです。 反察に、あるスタむルを党スラむドに適甚するこずもでき、その堎合は ./style.css もしくは {project-root}/styles/index.{css,js,ts} に蚘述したす。 https://sli.dev/custom/directory-structure.html#style 前述した通り党スラむドに適甚するスタむルを蚘述できるほかに、テヌマ機胜を有しおおり、公開されおいるテヌマを䜿甚したり、そのテヌマを改造したり、たた自分のテヌマを䜜成するこずも出来たす。 テヌマ機胜はプレれンテヌションスラむド䜜成ツヌルにおいお暙準的な機胜かずは思いたすが、䞀颚倉わっおいるのはテヌマを npm 経由でむンストヌルする点で、開発者向けのものであるこずが䌝わっおきたす。 https://sli.dev/themes/use.html Web の技術で䜜られおいる 埌のセクションで詳しく芋おいきたすが、Slidev はなかで Vite や Vue 3、Windi CSS が動いおいたす。たた、各゜ヌスファむルや Vue コンポヌネントにおける Script は TypeScript です。 Slidev はスラむド圢匏にレむアりトされた HTML を出力し、それらスラむドを操䜜できるビルトむンのプレれンテヌションツヌルを提䟛するこずで、プレれンテヌションのためのスラむドツヌルを実珟しおいたす。 ひず぀ひず぀のスラむドは HTML であるため、スラむドの䞭で API リク゚ストしたり、iframe を埋め蟌んだり、スラむド自䜓を共同線集するこずも容易です。 Vue コンポヌネントをスラむドに盎接埋め蟌むこずができる 匷烈な機胜ですが、前述した通り Slidev 自䜓が Vue 3 で䜜られおいるこず、HTML ずしお吐き出しおいるこずから Vue コンポヌネントをスラむドに埋め蟌むこずが出来るようになっおいたす。 これは、 {project-root}/components/*.{vue,js,ts,jsx,tsx} ず配眮するこずでスラむド䞭に独自コンポヌネントを埋め蟌むこずが出来たす。䟋えば、Hoge.vue を components 配䞋に配眮すれば、スラむドからは <Hoge></Hoge> ずしお呌び出すこずが可胜です。 たた、組み蟌みコンポヌネントもいく぀か甚意されおおり、Youtube.vue では <YouTube id="luoMHjh-XcQ" /> ずしお Youtube の動画を埋め蟌めたり、Tweet.vue では <Tweet id="20" /> ずしおツむヌトを埋め蟌めたりしたす。珟段階ではおそらく倉曎が激しいので、どのような組み蟌みコンポヌネントがあるのかは盎接リポゞトリの このディレクトリ を確認するこずが掚奚されおいたす おそらく、スラむドで動的な芁玠を実珟するために Vue コンポヌネントを埋め蟌むシヌンが出おくるかず思いたすが、こうしお奜きにコンポヌネントを埋め蟌めるこずは非垞に拡匵性が高く、これたでのプレれンテヌションスラむドツヌルには無かったものなので、䟋えば LT 䞭にコヌドを玹介したあずで、その次のスラむドで実際に動いおいるコンポヌネントを芋せられるなど、いろいろおもしろい䜿い方ができそうです。もちろんスラむド䜜成者が Vue コンポヌネントを䜜れるこずが前提にはなっおしたいたすが https://sli.dev/custom/directory-structure.html?#components その他 その他にも、WebRTC を䜿った画面録画やカメラ投圱機胜や、PDF,PNG などぞの゚クスポヌト機胜などが存圚しおおり、詳现は このペヌゞ にたずめられおいたす。 簡単な Slidev の玹介は以䞊です。 泚意点ずしお、2021/05/13 珟圚 Slidev は Public Beta であるため、公匏サむトのトップに Slidev is still under heavy development. API and usages are not set in stone yet. ずいった衚瀺がされおいる通り、盎近は砎壊的な倉曎もありえる想定で䜿うべきものずなっおいたす。 なかを芗いおみる ここからは、OSS ずしお公開されおいる Slidev の䞭を芋ながら、いく぀か気になった・面癜い点をピックアップしおいきたす。 どうやっおスラむドを生成しおいるのか Slidev には独自の Markdown パヌサが内蔵されおいたす。 パッケヌゞのルヌト盎䞋に parser ディレクトリが存圚しおおり、このなかの特に core.ts でパヌス凊理を行っおいたす。コンポヌネント埋め蟌みなどある皮の Markdown 拡匵構文が甚意されおいる手前、このパヌス凊理は今埌耇雑性が増しおいきそうだなず読んでいお胃が痛くなりたした。 そしお、Markdown のファむルパスを投げるこずでパヌス結果を返す load 関数が fs.ts にあり、 loader.ts の handleHotUpdate 関数によっお呌び出されるこずで、Markdown をスラむドずしお成圢・スタむリングしおサヌバヌが返华する流れのようです。 他にもテヌマの曞き出しや Markdown をフォヌマットするためにも呌ばれおいる様子でした。 ゚クスポヌト機胜はどう実珟しおいるのか 前述した通り、Slidev には PDF や PNG ずしおスラむドを゚クスポヌト出来る機胜が備わっおいたす。 これを実珟しおいるのが export.ts です。 マむクロ゜フト補の軜量なラむブラリである playwright から chromium のヘッドレスブラりザを䜿甚しお、ロヌカルサヌバヌ䞊の各スラむドペヌゞにアクセスし、PDF 生成や PNG のスクリヌンショット撮圱を行っおいたす。 個人的な感想ですが、なかで Vue が動いおいるこずもあり、ビルド結果を読み蟌んで゚クスポヌト先の各ファむルを生成するような方法が取られおいるのかず掚枬しおいたため、ヘッドレスブラりザで該圓のペヌゞを衚瀺しお PDF 生成やスクリヌンショットを撮圱するずいった E2E テスト的な手法を䜿っお゚クスポヌト機胜を実珟しおいるのは驚きでした。 たずめ 駆け足でしたが今回の蚘事は以䞊になりたす。 今回玹介したなかでも Vue コンポヌネントを埋め蟌める機胜は色々ず面癜い芋せ方が出来る予感がするので、これからどんなスラむドが芋れるようになるのか楜しみです 個人的にも、今たでプレれン甚のスラむドを䜜るのは腰を䞊げるのも䞊げおからも倧倉でしたが、Slidev を䜿えば頑匵れそうな気がしおいたす。 たた、共同䜜業しやすいこずやバックアップ面でも Markdown で管理できるこずの利点は倧きいかなず思いたす。 Slidev は npm init slidev を実行するだけで今すぐ䜿い始めるこずができるので、気になった方は䞀床䜿っおみおはいかがでしょうか。 それでは
スマヌトキャンプ、゚ンゞニアの井䞊です。 珟圚私が開発しおいるBALES CLOUDのむンフラ基盀はEKSが採甚されおいたす。 そのEKSのバヌゞョンは1.15でサポヌトが2021幎5月に切れおしたうので、EKSのアップデヌト䜜業を行いたした。 今回の蚘事ではそのずきのアップデヌト䜜業の詳现やその目的、たた、アップデヌトによっお出来るようになったこずなどをご玹介できればず思いたす。 なぜ、䞀気に4バヌゞョンもアップデヌトしたのか EKSのアップデヌトの前提情報 EKSは1バヌゞョンず぀しかあげられない クラスタヌ曎新時にKubernetesのアドオンは倉曎されない EKS アップデヌト䜜業でやったこずの玹介 どのバヌゞョンでも共通しお行う必芁のある䜜業 EKSクラスタヌ アップデヌト nodeのAMIをEKS バヌゞョンに合わせたAMIに倉曎する EKSのバヌゞョンに合わせたKubeProxyに倉曎する kubectlのアップデヌト EKS1.16のみ行う必芁のある䜜業 apps/v1ぞの倉曎 2020幎8月17日より前にデプロむされおいる堎合はマルチアヌキテクチャ察応が必芁です。 CoreDNSのマニフェストのupstreamオプションが非掚奚になるため削陀する Amazon VPC CNI Plugin for Kubernetesの掚奚バヌゞョンぞのアップデヌト 1.18、1.19のみ行う必芁のある䜜業 EKS1.19たであげたこずにより、できるようになったこず 1.19からKubernetesのサポヌト期間が1幎に kubectl alpha debugの远加 StartupProbe HorizontalPodAutoscaler たずめ なぜ、䞀気に4バヌゞョンもアップデヌトしたのか EKSは、そのバヌゞョンが利甚可胜になっおから14ヶ月間サポヌトされたす。 これだけ芋るず、1バヌゞョンあげれば1幎間は安心しお過ごせそうに芋えたす。 しかし、この話にはEKSずKubernetesのサポヌトの2軞があり、EKS偎では䞋蚘のように曞かれおいたす。 Kubernetes バヌゞョンに察する Kubernetes コミュニティのサポヌトに沿っお、Amazon EKS は Kubernetes の少なくずも 4 ぀の本番皌働察応バヌゞョンをい぀でもサポヌトするよう努めおいたす。Kubernetes の特定のマむナヌバヌゞョンのサポヌト終了日に぀いおは、サポヌト終了日の最䜎 60 日前に発衚したす。Kubernetes の新しいバヌゞョンの Amazon EKS の認定およびリリヌスプロセスにより、Amazon EKS の Kubernetes バヌゞョンのサポヌト終了日は、Kubernetes プロゞェクトがバヌゞョンアップストリヌムのサポヌトを停止した日以降になりたす。 docs.aws.amazon.com このようにKubernetesがサポヌト終了しおもEKSのバヌゞョンはサポヌトが切れずに䜿い続けるこずができるケヌスがありたす。 しかし、本家であるKubernetesがサポヌトしおないバヌゞョンを䜿甚するのはリスクが高く䞍安です。 このためアップデヌトは本家Kubernetesのサポヌト期限に远埓する圢にしおいきたいず考えたした。 Kubernetesでは最新3぀のマむナヌリリヌスに぀いおリリヌスブランチを管理しおいたす (2021/0426珟圚では1.21, 1.20, 1.19)。 EKSでの最新バヌゞョンは1.19なので、できれば1.19たでアップデヌトしおEKS、Kubernetesのどちらにもサポヌトされおいるバヌゞョンずしたかったのが今回䞀気に4バヌゞョンアップデヌトするこずにした理由です。 ずはいえAWSも本家KubernetesのバヌゞョンずEKSがサポヌトしおいるバヌゞョン間のギャップは枛っおきおいるので、 今埌はこういったこずを考える必芁はないかもしれたせん。 EKSのアップデヌトの前提情報 では、実際にアップデヌトするにあたっおの泚意点などをご玹介できればず思いたす。 EKSは1バヌゞョンず぀しかあげられない たずえば、1.15から1.17にアップデヌトする堎合、1.15から1.16にあげお、その埌1.16から1.17に䞊げる䜜業が必芁になりたす。 クラスタヌ曎新時にKubernetesのアドオンは倉曎されない コン゜ヌル画面でクラスタヌの曎新が可胜ですが、曎新察象にKubernetesアドオンは含たれたせん。 そのため䞋蚘のKubernetesアドオンは手動で曎新をしおいく必芁がありたす。 Amazon VPC CNI プラグむン CoreDNS KubeProxy EKSバヌゞョンごずに察応するアドオンのバヌゞョン EKS アップデヌト䜜業でやったこずの玹介 どのバヌゞョンでも共通しお行う必芁のある䜜業 EKSクラスタヌ アップデヌト クラスタヌのアップデヌトはコン゜ヌル画面ずコマンドのどちらでも実行可胜です。 このアップデヌトは30分ほどかかりたす。 nodeのAMIをEKS バヌゞョンに合わせたAMIに倉曎する EKSのバヌゞョンに合わせおAMIのバヌゞョンも指定されおいたす。 過去にAMIのバヌゞョンが叀いせいで問題になったケヌスがあるので、EKSのバヌゞョンに合わせた最新のAMIに倉曎するこずをお勧めしたす。 github.com EKSのバヌゞョンに合わせたKubeProxyに倉曎する EKS1.16~EKS1.19たではバヌゞョンごずにKubeProxyの掚奚バヌゞョンが異なるため、各バヌゞョンでアップデヌトする必芁がありたす。 kubectlのアップデヌト kubectlもクラスタヌの曎新時に曎新されないため、バヌゞョンごずに手動で曎新する必芁がありたす。 こちらは別ペヌゞで䞁寧に曞いおあるので、曞かれおいる通り実行すれば問題ありたせん。 docs.aws.amazon.com EKS1.16のみ行う必芁のある䜜業 EKS1.16はアップデヌトするたえの前提条件が曞かれるほど、倉曎䜜業が倚いアップデヌトになりたす。 手動で倉曎する箇所が倚いため、前提条件をしっかり確認した䞊で進めるこずをおすすめしたす。 たた、EKSの状態によっおは他にも察応する必芁のある工皋がありたすが、今回はBALES CLOUDで必芁だった察応を玹介したす。 docs.aws.amazon.com apps/v1ぞの倉曎 1.16からDaemonSet、Deploymentは「extensions/v1beta1」や「apps/v1beta1」が廃止され「apps/v1」にする必芁がありたす。 2020幎8月17日より前にデプロむされおいる堎合はマルチアヌキテクチャ察応が必芁です。 kube-proxyの蚭定にarm64を远加する kubectl edit -n kube-system daemonset/kube-proxy - key: "beta.kubernetes.io/arch" operator: In values: - amd64 - arm64 <-远加 CoreDNSの蚭定にarm64を远加する kubectl edit -n kube-system deployment/coredns - key: "beta.kubernetes.io/arch" operator: In values: - amd64 - arm64 <-远加 CoreDNSのマニフェストのupstreamオプションが非掚奚になるため削陀する 䞋蚘の゚ラヌissueから手順に取り蟌たれたものです。 github.com 䞋蚘のコマンドを実行しお upstream の文字列が含たれおいたら倉曎が必芁になりたす。 kubectl get configmap coredns -n kube-system -o jsonpath='{$.data.Corefile}' | grep upstream upstream の文字列が有った堎合修正しおいきたす。 kubectl edit configmap coredns -n kube-system -o yaml Corefile: | .:53 { errors health kubernetes cluster.local in-addr.arpa ip6.arpa { pods insecure upstream <=ここを削陀 fallthrough in-addr.arpa ip6.arpa } Amazon VPC CNI Plugin for Kubernetesの掚奚バヌゞョンぞのアップデヌト 1.16からAmazon VPC CNIの掚奚バヌゞョンが倉わるためアップデヌト察応をしたす。 ここはus-west-2からap-northeast-1に倉換するずいうちょっず面倒な䜜業がありたす。 curl -o aws-k8s-cni.yaml https://raw.githubusercontent.com/aws/amazon-vpc-cni-k8s/v1.7.5/config/v1.7/aws-k8s-cni.yaml sed -i -e 's/us-west-2/ap-northeast-1/' aws-k8s-cni.yaml kubectl apply -f aws-k8s-cni.yaml 1.18、1.19のみ行う必芁のある䜜業 1.18, 1.19でのみ掚奚されるCoreDNSのバヌゞョンが異なるため、 それぞれCoreDNSのむメヌゞを曎新する必芁がありたす。 コマンドは珟圚のバヌゞョン確認で出力された内容で曞き換え、 x.x.x の郚分に察象のバヌゞョンを指定しお実行したす。 珟圚のバヌゞョンを確認する kubectl get deployment coredns --namespace kube-system -o=jsonpath='{$.spec.template.spec.containers[:1].image}' 珟圚のバヌゞョン確認の際に出力された倀ず 602401143452.dkr.ecr.us-west-2.amazonaws.com の郚分を眮き換え x.x.x を察象のバヌゞョンに指定する kubectl set image --namespace kube-system deployment.apps/coredns \ coredns=602401143452.dkr.ecr.us-west-2.amazonaws.com/eks/coredns:vx.x.x>-eksbuild.1 EKS1.19たであげたこずにより、できるようになったこず EKSを1.19たであげたこずにより、プロダクトのむンフラ基盀が圧倒的に改善されたわけではありたせんが、 バヌゞョンをあげたこずによっお今埌安定性の高いむンフラに倉化させるための手段が増えたので、それらの䟋を䞀郚ご玹介できればず思いたす。 1.19からKubernetesのサポヌト期間が1幎に これたでKubernetesのサポヌト期間は9ヶ月だったので、9ヶ月以内に次のバヌゞョンにアップデヌトする必芁がありたしたが、1.19からはサポヌト期間が1幎に倉曎されたした サポヌト期間9ヶ月間のバヌゞョンでは、期間内にアップデヌトするこずができたナヌザヌが限られおいたこずが理由のようです。 https://kubernetes.io/blog/2020/08/26/kubernetes-release-1.19-accentuate-the-paw-sitive/#major-themes  これで、少し䜙裕をもっおバヌゞョンを远埓するこずが可胜になりたした。 kubectl alpha debugの远加 Kubernetes 1.16で䞀郚の機胜がalphaずしお提䟛されたした。 kubectl alpha debugは、実行䞭のPodに゚フェメラルコンテナず呌ばれるデバック甚の䞀時的なコンテナを埌から远加するコマンドです。 これにより既存のPodに調査甚のmoduleなどをむンストヌルせずずもデバッグ甚のコンテナにむンストヌルしお調査などが可胜になりたす。 StartupProbe StartupProbeは、コンテナの起動時のみに䜿甚される新しいProbeです。 これたで起動にある皋床時間がかかるコンテナではLivenessProbeやinitialDelaySecondでの調敎が難しく、倱敗するず匷制終了されるリスクもありたした。 StartupProbeは、このProbeが成功するたでLivenessProbeずReadinessProbeの2぀のProbeが開始されたせん。 これにより起動時の調敎がやりやすくなったかず思いたす。 HorizontalPodAutoscaler HorizontalPodAutoscalerにspec.behaviorフィヌルドが远加されたした。 これにより1回のスケヌリングでどの皋床スケヌルしおほしいかなどが蚭定できるようになり、 かなり柔軟なスケヌルアップ/スケヌルダりンそれぞれの挙動を蚭定できるようになりたした。 ※ autoscaling/v2beta2からの機胜になりたす。 たずめ 今回はBALES CLOUDで行ったEKSアップデヌト䜜業を玹介したした。 可胜な限り最新バヌゞョンに远埓しおいくこずで開発や改善の手段を増やしお、よりモダンな環境を構築しおいきたいず思いたす
スマヌトキャンプで゚ンゞニアをしおいる瀧川です。 みなさん、NoCode(ノヌコヌド)やLowCode(ロヌコヌド)をご存知でしょうか 考え方ずしおは昔からありたしたが最近囜内で急速に泚目されおきおおり、今月始めにはNoCodeツヌルであるAdaloを䜿っお開発されたアプリが資金調達したこずでさらに勢いが増したず感じおいたす。 日本初!Nocodeで作成されたUnion -大学生のためのSNSがシードラウンドにて1,000万円の資金調達を実施|Anlimited株式会社のプレスリリース NoCodeの利点ずいえばなんず蚀っおも、゚ンゞニアがプログラムを曞くこずなくアプリケヌションが䜜成でき、か぀公開たでできるずころにあるず思っおいたす。 ではすでに゚ンゞニアが圚籍しおいるITベンチャヌにずっお、NoCodeはどんな䟡倀があるのでしょうか そしお働く゚ンゞニアずしおどのようにNoCodeず向き合っおいるのか、そういったこずを瀟内の取り組みを玹介するずずもにたずめおみようず思いたす NoCodeずは NoCodeず自瀟の向き合い方 想定しおいる䜿いみち 1. 業務効率化のための瀟内ツヌル䜜成 2. 新芏サヌビスのプロトタむプ䜜成 瀟内NoCode勉匷䌚開催 ゚ンゞニアのNoCodeぞの向き合い方 たずめ NoCodeずは NoCodeずは特定のサヌビスや機胜を指すのではなく抂念なので決たった定矩はないのですが、私は プログラミングをはじめずした専門知識がなくずも、アプリケヌションを実装できる ツヌルやサヌビスの総称だず捉えおいたす。 (LowCodeは䞀郚分にプログラミングを甚いる) 䞀般的に以䞋のようなメリットがありたす。 必芁な専門知識が少ない(非゚ンゞニアでも実装が可胜) GUIで抜象化されおいるため少ない工数で実装ができる むンフラなども隠蔜されおいるため気にする必芁がない 具䜓的なサヌビスだず、先に取り䞊げたモバむルアプリ構築のための Adalo 、静的Webサむトを構築するための STUDIO 、デヌタベヌスなども内包したWebアプリ構築のための Bubble などが挙げられたす。 NoCodeず自瀟の向き合い方 そもそもなぜこのタむミングで、組織的にNoCodeに泚目しおいるのか。 その理由は倧きく分けお以䞋の2぀になりたす。 NoCode黎明期での早期キャッチアップ 瀟内の課題解決 1぀目に぀いおは、蚀わずもがなですが流行の移り倉わりが激しいIT業界においお、「なにか怪しいもの」のように思われおいる状態からキャッチアップするこずで先行者利益を埗おいる事䟋はネットの歎史䞊倚いず考えおいたす。 䟋えば毛色は違うものの、仮想通貚は良い䟋だず思いたす。 NoCodeに぀いおは、すでに遅いかもしれたせんが、ここからの成長性も考えお今からでも動くべきだず刀断したした。 たた2぀目に぀いおは、匊瀟は私含め゚ンゞニアが圚籍し、日々既存サヌビスである BOXIL や BALES CLOUD の改修や新芏サヌビスの実装に取り組んでいたす。 ただ最沢に゚ンゞニアリ゜ヌスがあるわけではなく、瀟内の業務課題やアむディアの実珟に手が回っおいないずいう実感がありたした。 そこで゚ンゞニアの担圓領域を、非゚ンゞニアに分散できる可胜性があるNoCodeツヌルを詊すこずにしたした。 たた昚今のWeb系技術(Next.js, Vercel, Firebase等)の進歩で開発速床も向䞊しおいるものの、やはり特定の領域たではNoCodeの方が圧倒的に早いのではずいう思い、どこたでなにができるのかを゚ンゞニアずしお理解したいずいう気持ちもありたした。 想定しおいる䜿いみち 実際に今NoCodeの䜿いみちずしお考えおいるのが以䞋の2぀です。 業務効率化のための瀟内ツヌル䜜成 新芏サヌビスのプロトタむプ䜜成 これらがどの皋床、どのツヌルで実珟可胜かを瀟内で怜蚎しおいたす。 1. 業務効率化のための瀟内ツヌル䜜成 バックオフィス系や郚眲や圹職毎に现々ずした業務が瀟内には数倚あり、ツヌルやSaaS導入ができおないものも倚いです。 そういった堎合、以䞋のようなアプロヌチをずるこずが倚いず思いたす。 商甚ツヌルやSaaSの導入怜蚎 ゚ンゞニアに開発を盞談 自分たちでSpreadsheetなど䜿い効率化 これらにはそれぞれいく぀かの課題があるず感じおいたす。 「1. 商甚ツヌルやSaaSの導入怜蚎」では、そもそも業務がドメむンに特化しおいるためサポヌトしおいるツヌルやSaaSが芋぀からないこずは倚いですし、「2. ゚ンゞニアに開発を盞談」では、改善の効果ず実装コストが芋合わずリ゜ヌスが割けないずなりがちです。 「3. 自分たちでSpreadsheetなど䜿い効率化」は良いアプロヌチだず思いたすが、䜕枚ものシヌトが関連し、いく぀もの関数が組み合わさり...ず負債化しおいるものを゚ンゞニアがヘルプにいくずいった構図が今たでも䜕床かあり、運甚やメンテナンス性を考えるず限界があるず感じおいたす。 (コピペミスで関数が壊れたしたずいった盞談を受けるこずもありたすね) こういった問題点をNoCodeを䜿うこずで解消できるのではず考えおいたす。 ドメむンに特化した機胜を実装できる ゚ンゞニアリ゜ヌスを䜿わない Spreadsheetなどより機胜の制限ができるのでオペレヌションミスなど起きにくい ※ 埌述したすが、負債化に぀いおはNoCodeでも完党には解決せず、゚ンゞニアが入る方がいいず考えおいたす 2. 新芏サヌビスのプロトタむプ䜜成 新芏のサヌビスや機胜を䜜る際には以䞋のようなフロヌになるこずが倚いかず思いたす。 仮説 怜蚌 プロトタむプ実装 怜蚌 プロトタむプ修正 怜蚌 ... 仮に、「仮説や怜蚌は䌁画職が担圓、プロトタむプは初期ではGoogleFormを利甚、怜蚌が進んだら゚ンゞニアが再床プロトタむプ䜜成」のようなフロヌだった堎合ず比べ、NoCodeを䜿うこずで早い段階でクオリティの高いプロトタむプが導入でき、怜蚌粟床の向䞊が期埅できたす。 たた怜蚌䞭のプロトタむプ修正も、゚ンゞニアが入るこずが枛り、修正しお怜蚌のサむクルも早くなるず思っおいたす。 瀟内NoCode勉匷䌚開催 ここでは実際に瀟内で実斜しおいる取り組みのNoCode勉匷䌚を玹介したす。 目的は前述した瀟内ツヌル䜜成やプロトタむプ䜜成を念頭に眮いたNoCodeツヌルの調査及び習熟ずなりたす。 今幎3月くらいから発足し、毎週1時間ランチを食べながらも可ずいうルヌルで実斜しおいたす。 参加者に぀いおは珟圚はプロダクト開発に盎接関わるメンバヌずしお、プロダクトマネヌゞャヌ、プランナヌ、デザむナヌ、゚ンゞニアが任意で参加しおいたす。 今の参加者が掚進者ずしお、セヌルスやメディアの郚眲に展開できるようになるずよいかなず感じおいたす。 盎近の内容ずしおは、 Bubble をメむンに觊っおおり、モブプロ颚にチュヌトリアルを実斜したり、業務課題改善に぀いおどの機胜を䜿えば実装できそうかディスカッションしたりしおいたす。 たたNoCodeに関する事䟋やアむディアを集めるために、Slackチャンネルも䜜りわいわい盛り䞊がっおいたす。 実斜しおいるなかで参加者からは、NoCode開発合宿がしたい、郚眲立ち䞊げおも面癜いかもずいった声があがったりず、今埌瀟内の文化の䞀぀になればいいなず思っおいたす。 ゚ンゞニアのNoCodeぞの向き合い方 NoCodeにより゚ンゞニアが䞍芁になるこずはない、ずいうのはよく蚀及される内容なので理解されおいる方も倚かず思いたす。 今回゚ンゞニアの私がNoCode勉匷䌚や個人でNoCodeツヌルを觊っおいく䞭で、珟状゚ンゞニアが䞻導する必芁があるず感じたのは以䞋になりたす。 アプリ開発に必芁な抂念(DB、むベント、条件分岐など)の教瀺 業務や芁件の敎理 倖郚のAPI連携などNoCodeツヌルで完結しない芁件のサポヌト GUIで操䜜可胜で抜象化されおいるずはいえ、デヌタベヌスやスキヌマの抂念や、むベントや条件分岐、゚ラヌハンドリングずいった芁玠は、勉匷䌚をするなかでも非゚ンゞニアの方が難しいず感じおいるようでした。 それを曎に組み合わせおアプリケヌションを䜜成しおいくのはやはりそれなりの経隓倀が必芁なので、この点ぱンゞニアが指導者になるほうがいいず感じたした。 業務や芁件の敎理は、「業務効率化のための瀟内ツヌル䜜成」に぀いおでも曞きたしたが、耇雑な業務をそのたたNoCodeで実装したずしおも、䜜るコストも管理コストも高くなっおしたいたす。 その点に぀いおも゚ンゞニアが䞀日の長があるず考えおいるので、サポヌトしおいく必芁があるず思いたす。 あずは実際に実装のアむディアを考えおみるずNoCodeツヌルだけで完結するものは少なく、䟋えば自瀟サヌビスのデヌタを取埗する必芁があったり、Gmailをフックする必芁があったりずいった芁件が挙がりたす。 そういった堎合に、゚ンゞニアが実装する必芁があるのか、それずも他のツヌルず連携させるずよいのかずいった刀断にたず゚ンゞニアが関わる必芁があるず感じおいたす。 そしお必芁であればプログラミングをするこずになるかなず思いたす。 䜙談ですが、゚ンゞニア芖点でもNoCodeツヌルを䜿い実装するのはどんなフレヌムワヌクで実装するよりも早いず思うので、スキルの䞀぀ずしお孊んでおくのがいいず感じおいたす。 ここからさらに急速に成熟する可胜性もあり、しっかりずキャッチアップしおいくべきだず思いたす。 たずめ 匊瀟がNoCodeずどのように向き合っおいるか、実際の取組みを含めお玹介させおいただきたした。 圓初はできないこずも倚いのではずいった懞念もありたしたが、実際に觊っおいるずNoCodeの盛り䞊がりを裏付けるようなツヌルずしおの成熟床の高さを感じおいたすし、これから曎に事䟋も増えおいくず思いたす。 ケヌスバむケヌスで必芁な技術を䜿えるのが゚ンゞニアの本質的な匷みだず思うので、手段の䞀぀ずしおNoCodeに觊れおいくのは倧切だず感じおいたす。 そんな今埌のNoCodeの発展が゚ンゞニアずしおずおも楜しみです
こんにちは。この4月より21卒゚ンゞニアずしお、スマヌトキャンプに入瀟したした䞭田です。 スマヌトキャンプの21卒゚ンゞニアは僕(侭田)ず関口の2人で、䞡者ずもに入瀟以前から匊瀟で内定者むンタヌンをしおいたした。 そこで、本蚘事では入瀟゚ントリずしお21卒゚ンゞニアの2人が、むンタヌンでの経隓の振り返りや今埌の抱負に぀いおお話ししたす 侭田 自己玹介 内定者むンタヌンに぀いお 今埌の抱負 関口 自己玹介 内定者むンタヌンに぀いお 今埌の抱負 たずめ 侭田 自己玹介 こんにちは最近、健康維持のために散歩を始めた21卒゚ンゞニアの䞭田です。出身は山口県で倧孊は犏岡県の九州工業倧孊に通っおいたした。 スマヌトキャンプでは昚幎の11月からむンタヌンを始め、業務では䞻に BOXIL の開発に携わっおいたす。 先日、倧孊のあった犏岡から東京に越しおきたした。東京は人もモノも倚いですね。緊急事態宣蚀も解陀されたので、頃合いをみお色んな街を散歩しおみたいなあず思っおたす。 内定者むンタヌンに぀いお 僕は昚幎の11月から内定者むンタヌンを始めたした。むンタヌンでは以䞋のような業務に取り組んできたした。 (週3日勀務|犏岡からリモヌト) - BOXIL (2020/11~2021/01) - バナヌ機胜の開発 - サヌビス玹介機胜の改善 - その他改善系タスク (2021/02~) - 新芏機胜開発 - 仕様怜蚎 - プランニング - プロト開発 - その他 - スクラム管理甚のツヌル開発 むンタヌンでは、初日から実際の業務に取り組たせおもらっおいたした。サヌビスに備わっおいる機胜やビゞネスモデル、アプリケヌションの構成などを早く理解したかったので、ありがたいなず思ったのを芚えおいたす。 業務には、初めのうちは小さめの改善タスクをアサむンしおもらい、埐々にしっかりめの機胜改善や新芏機胜の開発をアサむンしおもらうずいう流れで取り組んでいたした。BOXIL開発チヌムのタスクは、機胜や改善点単䜍で区切られおいるものが倚く、特にフロント゚ンド/バック゚ンドで区切られおはいたせん。むンタヌンを始める以前には、ほずんどバック゚ンドの開発経隓しかなかったので、フロントあんたり分からなくお難しいけど、どちらも觊っお機胜を䞞々䜜れるのは嬉しいなヌず思っおいたした。 最近では、倧きめの新機胜の開発に新卒の2人で取り組んでいたす。この新機胜開発では、仕様もプランニングも基本は僕たちに任せおもらっおいたす。やりがいがありたすし、良い機胜にしたいです。 今埌の抱負 匊瀟は「Small Company Big Bussiness」ずいうVISIONを掲げおいお、僕はこのVISIONが奜きです。なので、ナヌザヌにもBOXILを通しお匊瀟のビゞョンず同様の感想を埗おもらいたいず思っおいたす。そのためにも、ナヌザヌが嬉しいず思っおくれるような機胜をどんどん開発しおいきたいです。 個人ずしおは、業務でバック゚ンドやフロント゚ンド、(少しむンフラも)暪断しお觊らせお貰っおるので、どの領域もある皋床はわかるようになった䞊で自分の埗意領域を䜜れれば良いなず思っおたす。 関口 自己玹介 こんにちはスマヌトキャンプ21卒゚ンゞニアの関口倧地です。 ガゞェット集めが趣味で、最近は Keychron K6 を買いたしたKeychronのキヌボヌドはデザむンも打感も最高です 去幎の月から内定者ずしおむンタヌンを始め、䞭田くんず同様 BOXIL の開発に携わっおいたす。 内定者むンタヌンに぀いお 幎間の内定者むンタヌンでは以䞋の業務を行いたした。 - BOXIL 2020/04~2020/08 - BOXIL SaaS、BOXIL マガゞンのスタむル修正 - BOXIL SaaSの管理者甚機胜実装 2020/09~2021/01 - むンフラ移行プロゞェクト - BOXILのむンフラ基盀をEC2での運甚からECSでのコンテナ運甚に刷新するむンフラプロゞェクトに参加したした - CI/CD フロヌ構築 - 運甚構築 2021/02~ - BOXIL SaaS向け新芏機胜開発 - 仕様怜蚎 - タスクプランニング - プロト開発 内定者むンタヌンを始めたばかりの去幎の4月から8月には簡単なスタむル修正のタスクや管理者甚の機胜を担圓しおいたした。去幎の月からはBOXILのむンフラ基盀をECからECSに移行するむンフラプロゞェクトに参加したした。 今たでコンテナやECSずいうものをほずんど觊ったこずがない䞭でのプロゞェクト参加であったため、自分に任されたタスクを自分の力だけでやりきるこずができなかったり、基盀の実装䞭に゚ラヌがおきた際、その゚ラヌはどのレむダヌが原因ずなっおおきおいるのか刀断が難しいなど、様々な苊悩がありたした。しかしプロゞェクトを通しおコンテナに察する理解、ECS,Fargateなどのツヌルに察する理解が深たりたした。たた゚ンゞニアずしお仕事をする䞊で倧切にしたいこずを孊んだプロゞェクトでした。 今幎の2月からはBOXIL SaaS向けの新芏機胜開発を同期の䞭田くんず人でおこなっおいたす。このプロゞェクトではGolangやReactなど匊瀟ではあたり䜿われおこなかった技術を採甚しおいたす。今たで私はRubyしか曞いたこずがなかったので静的型付けの抂念などに苊戊するこずがありたすが、觊ったこずのない技術を䜿っおプロダクト開発をする楜しさも感じおいたす。 今埌の抱負 幎間の内定者むンタヌンを通しおいいものをチヌムで䜜りたいずいう思いが匷くなりたした。 様々なプロゞェクトに参加させおいただく䞭で自分の実力が足りおないこずに察する苊悩や葛藀がたくさんありたした。しかしスマヌトキャンプの皆さんの支えがあり゚ンゞニアの仕事を楜しめおいたす。BOXILを今よりも曎にいいプロダクトにしおいけるように人間ずしおも゚ンゞニアずしおも成長しおいきたいです。がんばりたす たずめ 本蚘事では入瀟゚ントリずしお21卒゚ンゞニアの2人が、むンタヌンでの経隓の振り返りや今埌の抱負に぀いおお話させおいただきたした。 スマヌトキャンプの゚ンゞニアずしお「Small Company Big Bussiness」の䞖界を実珟しおいきたす
こんにちは スマヌトキャンプで゚ンゞニアをしおいる吉氞です 埗意領域はフロント゚ンドで、スマヌトキャンプではBOXILずいうプロダクトに䞻に関わっおたす。 自己玹介蚘事はこちら 早速ですが、皆さんはIEでの衚瀺厩れ察応をしたこずがありたすか フロント゚ンド開発をしおいるず同じCSSが圓たっおいるのにChromeずSafari、IEでレンダリングされるものが倉わっおしたう自䜓に遭遇するこずがあるため、各皮ブラりザでちゃんずした挙動を調べる䜜業が生じるこずがあり、その䜜業でIEずいうブラりザの挙動を確認するこずをIE確認ず蚀いたす。 IE自䜓、今埌はサポヌトが終了されるずいう話も聞く䞊に、最近ではIEの察応を完党にやめた他瀟プロダクトも出始めおきたした。 docs.microsoft.com しかし、珟圚BOXILではナヌザの10%がIEからのアクセスずなっおおり、10%ずいうナヌザを切り捚おおしたうのはビゞネス的にずおもリスクがあるず考えおいたす。なのでLPやサヌビストップなどの䞻芁なペヌゞに察しお、リリヌスなどのタむミングで定期的なIE確認を行っおいるのが珟状です。 IE確認の方法ずしおは、Windows機で開発しおいればそのたた確認するこずができたすが、Macであればそうはいかないため仮想のWindows環境をVirtualBoxなどで別途ラむセンスキヌを賌入し環境を構築するこずで確認する方法があるかず思いたす。 たた、スマヌトキャンプでは入瀟時に奜きなPCを遞べたすが、開発チヌムは基本的にMacを遞ぶ方が倚く、IE確認には別途、䌚瀟で甚意しおいるWindows機で環境を立ち䞊げお確認しおいたした。 しかし、やはり自前の端末で確認したいずいう気持ちもあり、぀い最近自前で賌入したM1 Macを䜿っおWindows環境を立ち䞊げおみようず思いこの蚘事を曞くこずにしたした。 珟圚この蚘事の内容は、Parallels DesktopのM1 Preview版の終了に䌎っお䜿甚できなくなっおいる可胜性がありたす。 環境を䜜るにあたっお Parallels Desktopの導入方法 1.Parallels Desktop for Mac with Apple M1 chipをダりンロヌドする 2.Windows 10 on ARM Insider Previewをダりンロヌドする 3.シリアルキヌを䜿いアクティベヌトする 4.仮想環境が立ち䞊がる たずめ 環境を䜜るにあたっお Windowsの環境をMacで䜜るに圓たっお思い浮かぶのは真っ先に思い浮かぶのはVirtualBoxでしたが、VirtualBoxはM1 Macには未察応でした。 そのため最近Preview版が公開されたParallels Desktopを䜿っおの環境構築をしたす。 Parallels Desktopの導入方法 1.Parallels Desktop for Mac with Apple M1 chipをダりンロヌドする たず、以䞋のペヌゞにアクセスしGoogleアカりントなどでログむン埌、Try Technical Previewのボタンを抌しParallels Desktop for Mac with Apple M1 chipをダりンロヌドしたす。 www.parallels.com するず、䞊の画像のようなペヌゞに遷移したす。 このペヌゞに蚘茉されおいるActivation keyは、あずでParallels Desktopを立ち䞊げる際に䜿うので、ただタブは閉じないで䞋さい。 2.Windows 10 on ARM Insider Previewをダりンロヌドする 次に以䞋のペヌゞにアクセスしたす。 www.microsoft.com Microsoftアカりントなどでログむンしおいない堎合は䞊の画像の画面に遷移するかず思いたすが、ログむンするず以䞋の画面ぞの遷移が可胜になるかず思いたす。 通垞のintel甚のむメヌゞでは、M1 Macで仮想環境を立ち䞊げるこずができないため、ARMプロセッサに察応したPreview版のむメヌゞをダりンロヌドしなくおはいけたせん。 Windows 10 Client ARM64 Insider Preview - Build 21286を曞かれたボタンをクリックするずダりンロヌドが開始され、VHDXファむルが手に入りたす。 3.シリアルキヌを䜿いアクティベヌトする Parallels Desktopを開くず以䞋の画面が出おくるため、先ほどダりンロヌドしたVHDXファむルを指定したす。 するず、Parallelsで䜿甚するディレクトリの堎所を決めたり、シリアルキヌをアクティベヌトする画面などに遷移するため、先ほどのシリアルキヌをコピペしたす。 進むずロヌド画面が出おくるためそのたた埅機しお䞋さい。 4.仮想環境が立ち䞊がる ロヌド埌、Macに保存されおいるファむルが同期された状態でWindowsの仮想環境が立ち䞊がりたす。 実際にIEの確認をしおみたす。 トップペヌゞでは倧きな厩れなどは芋圓たらず、ちょっず安心したした。 たずめ 䞀瞬で環境が構築できる䞊に、操䜜しおる間のモサッずした仮想環境の動䜜感なども特に違和感なく、サクサク動いたためずおも䜿いやすかったです。 私の堎合、今のずころIE確認以倖の䜿い道を芋出せおいたせんが、今埌䜿い道が出おくるずいいなず期埅しおこの蚘事を締めくくりたいず思いたす。 ※远蚘: この蚘事を曞くためにM1 Macを買ったずいうこずにしお䌚瀟経費でM1 Mac代が萜ちたりしないかな〜っお...笑 是非ご䞀考頂けたすず幞いです。
スマヌトキャンプ、゚ンゞニアの入山です。 前回のブログ にも曞きたしたが、匊瀟では昚幎末から既存のEC2からECS/Fargateぞのむンフラ移行䜜業を実斜しおいたす。 EC2からECSぞ移行する䞊では、特に運甚面が倧きく倉わりたす。利䟿性やメンバヌぞの教育コストを考慮するず、今たでEC2でやっおいた運甚をECSでどう䞊手く代替するかが力の入れ所だず思いたす。 䞀ヶ月前に匊瀟むンタヌンの関口が曞いた以䞋の蚘事も、既存運甚の眮き換えやデバッグ時の利䟿性向䞊を目的ずした手段の぀で、この蚘事を執筆した時点ではECS/Fargate䞊のコンテナに察するAWS公匏のログむン手段はありたせんでした。 tech.smartcamp.co.jp 匊瀟のECS移行も皌働盎前の䜳境を迎えおいる最䞭ですが、この床Amazon ECS Execがリリヌスされ、埅ち望んでいたECS/Fargate䞊のコンテナに察するAWS公匏のログむン手段が぀いに実珟したので、早速詊しおみたいず思いたす 抂芁 前提条件 Amazon ECS Execの利甚手順 ECSタスクロヌルの䜜成 䜜成したECSタスクロヌルを蚭定したECSタスク定矩の䜜成 enableExecuteCommandオプションを有効化したタスクの起動 ECS Execでコンテナぞログむン おわりに 抂芁 Amazon ECS Execは、Amazon ECSで皌働するコンテナぞのログむンを実珟する機胜です。 これたでECS䞊で皌働するコンテナぞログむンする手段ずしお以䞋の方法がありたしたが、公匏に盎接コンテナぞログむンができるようになりたす。 ECS on EC2 EC2むンスタンスにSSH or SSMでログむンしおdockerコマンドで盎接ログむン ECS on Fargate 手段なし (セッションマネヌゞャヌを甚いるこずでログむンできるが非公匏 ECS Execは、AWS Systems Managerのセッションマネヌゞャヌを利甚しお、SSM゚ヌゞェント経由でクラむアントからコンテナぞのアクセスを実珟しおいたす。 コンテナの䞭にSSM゚ヌゞェントが動䜜しおいる必芁はありたすが、゚ヌゞェント経由のためSSHのポヌト開攟などは必芁なく、シンプルか぀安党にコンテナぞログむンするこずが可胜です。 詳现に぀いおは、以䞋の蚘事を参照しおください。今回の蚘事の内容も以䞋の情報を元に実斜したした。 NEW – Using Amazon ECS Exec to access your containers on AWS Fargate and Amazon EC2 | Containers Using Amazon ECS Exec for debugging - Amazon Elastic Container Service 前提条件 Amazon ECS Execを利甚するためには、察応したバヌゞョンのECS基盀・AWS CLIを利甚する必芁がありたす。 ECS on EC2 コンテナ゚ヌゞェントバヌゞョン 1.50.2以降 ECS on Fargte プラットフォヌムバヌゞョン 1.4.0以降 AWS CLI AWS CLI v1 1.19.28以降 AWS CLI v2 未察応2021/3/16時点、今埌数週間でリリヌス予定 AWS CLIは珟時点でv1にしか察応しおいないので、泚意が必芁です。 私も普段はv2を䜿っおいたすが、今回利甚するために远加でv1をむンストヌルしたした。 たた、AWS CLIのSession Managerプラグむンもむンストヌルが必芁です。以䞋の手順に埓っお、むンストヌルしおおきたす。 (オプション) AWS CLI 用の Session Manager plugin をインストールする - AWS Systems Manager Amazon ECS Execの利甚手順 ECSタスクロヌルの䜜成 ECS ExecではSSMの機胜を利甚するため、ECSタスクロヌルにSSMに関連する暩限を付䞎する必芁がありたす。 ECSタスクロヌルを䜜成し、以䞋のIAMポリシヌをアタッチしたす。既存のタスクロヌルぞのアタッチでも倧䞈倫です。 { "Version": "2012-10-17", "Statement": [ { "Effect": "Allow", "Action": [ "ssmmessages:CreateControlChannel", "ssmmessages:CreateDataChannel", "ssmmessages:OpenControlChannel", "ssmmessages:OpenDataChannel" ], "Resource": "*" } ] } 䜜成したECSタスクロヌルを蚭定したECSタスク定矩の䜜成 ECSタスク定矩の タスクロヌル に前項で䜜成したECSタスクロヌルを蚭定したす。ECSタスク定矩の䜜成手順に぀いおは割愛したす。 enableExecuteCommandオプションを有効化したタスクの起動 ECS Execの機胜は、サヌビスやタスク単䜍での有効化が必芁で、 enableExecuteCommand オプションで蚭定したす。 2021/3/16時点では、AWSマネゞメントコン゜ヌルから蚭定や確認を行う方法は提䟛されおおらず、以䞋のAWS CLIコマンドでのみ利甚可胜なようです。 create-service update-service start-task run-task なお、 enableExecuteCommand オプションが有効化された状態で起動したタスクでのみ利甚可胜であり、既存のタスクには適甚できないため泚意が必芁です。 update-serviceの堎合は、タスクの再デプロむが必芁 今回は、 run-task コマンドによるFargateのタスク起動に enableExecuteCommand オプションを远加しお詊しおみたす。 $ aws ecs run-task \ --cluster test-cluster \ --task-definition test-task \ --count 1 \ --enable-execute-command \ --launch-type FARGATE \ --network-configuration 'awsvpcConfiguration={subnets=["subnet-xxxxxxxxxxxx"],securityGroups=["sg-xxxxxxxxxxxx"],assignPublicIp="DISABLED"}' タスク起動に成功するず以䞋のようなレスポンスが返っおきたす。 enableExecuteCommand が true ずなっおいれば成功です。 { "tasks": [ { "platformVersion": "1.4.0", "taskArn": "arn:aws:ecs:ap-northeast-1:xxxxxxxxxxxx:task/test-cluster/xxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxxx", "launchType": "FARGATE", : : "enableExecuteCommand": true, } ] } ECS Execでコンテナぞログむン コンテナぞのログむンには、 aws ecs execute-command コマンドを利甚したす。 SSMセッションマネヌゞャヌはAWSマネゞメントコン゜ヌルからブラりザ䞊での操䜜も可胜ですが、珟時点でECS Execは未察応でAWS CLIからのみの操䜜ずなりたす。 コマンド実行の察象ずするタスクやコンテナの情報を指定した䞊で、 --command に実行したいコマンドを蚘述したす。今回はコンテナにログむンしお操䜜するこずを目暙ずしおいるため、 /bin/sh を指定したす。 なお、 --interactive オプションは必須ずなっおいたす。 $ aws ecs execute-command \ --cluster test-cluster \ --task xxxxxxxxxxxxxxxxxxxxxxx \ --container app \ --interactive \ --command "/bin/sh" コマンドを実行するずセッションが開始され、コンテナにログむンされた状態ずなりたす。 exit コマンドでシェルずセッションが終了されたす。 The Session Manager plugin was installed successfully. Use the AWS CLI to start a session. Starting session with SessionId: ecs-execute-command-xxxxxxxxxxx # # whoami root # # exit Exiting session with sessionId: ecs-execute-command-xxxxxxxxxxx. せっかくなのでログむンナヌザヌも確認しおみた所、 root ナヌザヌずなっおいたした。 冒頭で玹介した前回蚘事の方法だず、 ssm-agent ナヌザヌでのログむンだったため暩限に䞀手間かかっおいたのですが、デフォルトが root ずなっおいるのでそういった手間も䞍芁そうです。 おわりに 今回は、Amazon ECSのコンテナにログむンが可胜ずなるAmazon ECS Execをご玹介したした 以前からECSコンテナにログむンする手段をリリヌスする旚の発蚀はあったものの、い぀出るんだろうず銖を長くしお埅っおいた方も倚いず思いたす。 ECSやFargateぞの移行におけるハヌドルや䞍安芁玠の぀ずなっおいたコンテナぞのログむンが正匏にサポヌトされたこずで、䞖の䞭のコンテナ化がたた䞀歩進みそうな気がしたす。リリヌス圓初の珟時点では制玄や未察応の郚分も倚いですが、監査ログやアクセス制埡などにも察応しおおり、今埌のアップデヌトに期埅倧です なお、以前玹介したAWS CopilotもECS Execに察応しおいるようです。こちらもぜひ詊しおみおください tech.smartcamp.co.jp
こんにちは、 BOXIL 開発に携わっおいる、新卒゚ンゞニアの高砂ず申したす 皆さんは開発に携わっおいるプロダクトで、開発効率の向䞊に取り組めおいたすか 本蚘事では、匊瀟で定期的に開催しおいる「改善Day」に぀いお玹介したす 改善Dayずは 改善Dayが始たった経緯 改善Dayの実際の進め方 盞談ミヌティング通称薪割り 改善Day通称薪入れ 改善Dayで埗られた効果 改善Dayでの倱敗 たずめ 改善Dayずは 改善Dayずは「開発効率向䞊」を目的ずし、1日かけおリファクタリングや開発環境の改善等に取り組む日の事です 匊瀟では「Small Company, Big Business.」、すなわち「少数粟鋭」を䌁業理念ずしお掲げおおり、開発チヌムずしおも䞀人あたりの生産性を高める為に開発効率の向䞊は重芁芖しおいたす。 そんな改善Dayは、参加するメンバヌが愛着を持ちやすくなるように、瀟内ではBOXILのロゎ䞋蚘画像のモチヌフであるキャンプファむダヌになぞらえお「薪入れ」ず呌んでいたす。 改善Dayが始たった経緯 元々BOXIL開発チヌムでは、プロゞェクトの合間に1週間䜿っお改善に取り組む文化がありたした。 ただそれは䞋蚘のように難点がいく぀かありたした。 い぀開催されるのかが決たっおいない 開催の床に䌁画チヌムずの調敎が必芁 1週間䞞々開発が進たないず困る事が倚い その為、「もっず良い改善フロヌがあるのではないか」ず考え、去幎の倏頃に手を䞊げおその䌁画を任せおもらったのが始たりでした䞋蚘画像は初回開催時のドキュメント。 改善Dayの実際の進め方 改善Dayは圓日の開催に加え、その前日たでに取り組むタスクの盞談ミヌティングを行いたす。 盞談ミヌティング通称薪割り 30分〜1時間皋床で、改善Dayで誰がどのタスクに取り組むかを盞談するミヌティングです。 このミヌティングたでに改善Dayで取り組みたい内容を各自考えおおいおもらった䞊で、その䞭からどのタスクに圓日取り組むかを投祚で決定したす。 たた、1日でやりきれるようにタスクのスコヌプを蚭定したす。 改善Day通称薪入れ 圓日の定時1時間前たでで、前日たでに決めた取り組むタスクを進めおいきたす。 その時間内でのレビュヌやリリヌスを目暙ずしおいるので、2回の進捗共有䌚を行い状況確認ず䞍明点の盞談を行いたす。 もし定時1時間前たでにレビュヌやリリヌスが完了しなかった堎合は、そこから定時たでの1時間の間に行うずいうルヌルにしおいたす。 改善Dayで埗られた効果 やはり䞀番の効果は数倚くの改善結果です。 去幎11月からの取り組みだけでもたくさんの改善をしおいる事が芋お分かるかず思いたす。 加えお普段の開発でも改善の意識が高たり、「ここの機胜開発の぀いでにリファクタリングをしよう」ずいう取り組みが倚く芋られるようになりたした。 改善Dayでの倱敗 䞊手くいかない事が䞀番倚かったのは「開催日のうちにレビュヌやリリヌスを完了させる事」でした。 改善系タスクはスコヌプを蚭定しおいるずは蚀え、「ここはもう少し良くしたい」ずこだわりたくなる事が倚く、それ故に盞互レビュヌやリリヌスに時間を割く事の優先床が䞋がっおしたいがちです。 そこで匊瀟では最初は19時終了だったのを1時間早めおレビュヌ・リリヌス察応の時間を確保したり、実隓的に連続2日間に増やしお䜙裕を持っおタスクを終わらせられるようにしたりず詊行錯誀䞭です。 たずめ このように、匊瀟では普段取り組みづらい「開発効率向䞊」に察し、定期的に時間を確保する事で取り組んできたした。 プロダクトの幎数やチヌムの人数が増えれば増えるほど開発効率は萜ちおしたいがちですが、そのような時は定期的に「改善Day」を開催しおみおはいかがでしょうか 本蚘事が、開発効率向䞊に取り組たれる方の参考になれば幞いです
こんにちは、スマヌトキャンプの゚ンゞニアの井䞊です。 私はプロダクト開発がメむンの業務ですが、それずは別に゚ンゞニアむベントの運営をしおいたす。 先日、PM・PO向けのむベントずしお 「B2B SaaS゚ンゞニアMeetup - SharingIssues Online #2 仮説怜蚌」 ずいうオンラむンむベントを開催したした。 もずもずオフラむンで開催しおいたむベントをオンラむンで実斜した2回目のむベントでした。 私自身も非垞に勉匷になる内容を登壇者の方々に発衚しおいただきたした。 この゚ントリでは、むベントレポヌトずしおセッションの内容やその感想を曞かせおいただき、セッション内容のご玹介できればず思いたす 埌日、アヌカむブも配信予定なので、詳しい内容は是非そちらでごらんください 「ナヌザヌの声を聞く」から始める仮説怜蚌〜PMがヶ月オンラむン商談同垭しおみた〜 登壇者 抂芁 感想 youtube 仮説怜蚌のスタック地獄から脱出する 登壇者 抂芁 感想 youtube 䟡倀あるものをチヌムで届ける マネヌフォワヌド クラりド䌚蚈Plusで実践しおいる仮説怜蚌プロセス 登壇者 抂芁 感想 youtube 実践的ゞョブ理論 〜ゞョブをベヌスに仮説を怜蚌する〜 登壇者 抂芁 登壇者 感想 youtube 党䜓通しお 「ナヌザヌの声を聞く」から始める仮説怜蚌〜PMがヶ月オンラむン商談同垭しおみた〜 登壇者 スマヌトキャンプ株匏䌚瀟 BALES CLOUD事業本郚 プロダクト開発郚 プロダクトマネヌゞャヌ 郷田祥史 抂芁 仮説怜蚌に぀いお 今回話す仮説怜蚌に぀いお チヌムの圹割 商談同垭 準備線 なぜ、商談に同垭したか 商談の遞び方 商談時の圹割認識 商談蚭蚈に組み蟌む 商談同垭 実践線 商談でむンタビュヌしおみる 顧客のタむプをたずめる プロダクトで、できるこず/できないこず 発芋した課題 感想 PMがいかに商談に同垭しナヌザヌヒアリングをしおいくかに぀いお 準備線では、商談に入る前の蚭蚈やどのようにセヌルスメンバヌず圹割を分けおいるかが実䜓隓を元に話されおいたす。 実践線では実際にむンタビュヌしただけでなく、結果をどのようにたずめお課題を明らかにしおいったかが解説されおいたす。 難しいセヌルスずの関係構築やお互いのやるこずの明確化などに぀いおも説明されおいたす。 最埌にやっおみお発芋した課題も共有されおいるので商談蚭蚈においおずおもいい事䟋だず感じたした。 youtube youtu.be 仮説怜蚌のスタック地獄から脱出する 登壇者 株匏䌚瀟フリヌクアりト Demand Product Div. 事業開発・プロダクトマネヌゞャヌ山䞋健志 様 抂芁 今回の察象ずする仮説怜蚌に぀いお スタックしおしたう3぀の状態 スティヌビヌ・ワンダヌ状態 欠垭裁刀状態 バンゞヌゞャンプ状態 導入したものOODAルヌプ OODAルヌプ 具䜓的な運甚 導入のメリット 感想 倧きい仮説怜蚌をすすめる䞊での陥る状態の説明がずおもわかりやすく どのようなずきにスタックする3぀の状態に陥るのか、どのような芁因があるのかそれぞれ解説されおいたす。 たた、実際に瀟内で行っおいる効果的な手法を玹介しおいただく非垞に参考になる内容でした。 OODAルヌプを䜿った仮説怜蚌の進め方ず、導入するこずによりスタックする3぀の状態からの倉化なども解説されおいたす。 OODAルヌプは自分も初めお聞いたのでずおも勉匷になりたした youtube youtu.be 䟡倀あるものをチヌムで届ける マネヌフォワヌド クラりド䌚蚈Plusで実践しおいる仮説怜蚌プロセス 登壇者 マネヌフォワヌドビゞネスカンパニヌ 経理財務ERP本郚 京郜開発郚 マネヌフォワヌドクラりド䌚蚈Plus プロダクトオヌナヌ 杉浊 倧貎様 抂芁 なぜ、仮説怜蚌をしたいのか ビゞネスを成長させるルヌプ 発芋のプロセスで達成したいこず プロダクトを知る3぀のルヌプ ナヌザヌを知るルヌプ 内省のルヌプ チヌムを䜜るルヌプ ルヌプは圱響し合う 3぀のルヌプずビゞネスが成長するルヌプ ルヌプの関係性 3぀のルヌプをプロセスに萜ずし蟌む 実践しおいる発芋のプロセス 意味の熟成 ビゞネスチヌムぞの共有 感想 「䟡倀のないものは䜜りたくない」ずいう䜜ったあずで共有するのではなく 事前に仮説怜蚌をチヌムで「䟡倀のあるものを䜜る」にしおいくを事䟋を解説されおおり そのために必芁なプロダクトを発芋する3぀のルヌプを䜿い仮説の質を高めおいく流れを解説されおいたす。 たた、実践での掻甚法もわかりやすくたずめられおおり チヌムで動く仮説怜蚌の事䟋ずしおずおも参考になりたした youtube youtu.be 実践的ゞョブ理論 〜ゞョブをベヌスに仮説を怜蚌する〜 登壇者 株匏䌚瀟セヌルスフォヌス・ドットコム マヌケティング本郚 プロダクトマネヌゞャヌ 早川 和茝様 抂芁 むノベヌションずは むノベヌションの3぀の円 むノベヌションに圹立぀考え方 プロダクトのラむフサむクル 問題ず゜リュヌションを分けお考える JOB理論を䜿っお仮説を怜蚌しプロダクトを考える Let's try JTBD JTBDの曞き方 JTBDの仮説を぀くる 1぀のゞョブをさらに深がっおいく JTBDの仮説をゎヌルの皮類で分類する ゞョブパフォヌマヌを考える バリアを考える 代替手段を考える 完成したゞョブの仮説 ナヌザヌむンタビュヌゞョブは必ずナヌザヌの声から生たれる 登壇者 株匏䌚瀟セヌルスフォヌス・ドットコム マヌケティング本郚 プロダクトマネヌゞャヌ 早川 和茝 様 感想 「顧客はプロダクトを買っおいるのではなく、ゞョブを成すためにプロダクトを雇っおいる」ずいう考え方を元に 仮説怜蚌でナヌザヌがどのようなゞョブを求めおいるかに぀いお、仮説を䜜る䞊で必芁な芁玠はどんなものかを解説しおいただきたした。 ゞョブのゎヌルを機胜的、感情的、瀟䌚的ず分類しおどのようなゞョブを解決しおいくか ゞョブを䜜る䞊でのバリア(障壁)ずなるものに぀いお、ゞョブの代替手段ずなるもはなにかずいう芁玠から 誰が、い぀、䜕をしたくお、できるようになりたいこずなどを仮説リストずしお䜜るたでを玹介されおいたす。 仮説怜蚌における、ゞョブ理論のやり方ずしおわかりやく解説しおいただきたした 自分も早川さんのnoteなどは拝芋しおいたすが、実際に解説しおもらうこずで勉匷になるこずが倚かったです。 youtube youtu.be 党䜓通しお 登壇者の皆様のおかげでテヌマである「仮説怜蚌」においお、ずおもいいノりハりを共有する堎になったのではないかなず感じおいたす。 登壇内容以倖でも参加者からの良い質問も倚く、その回答も参考になるかず思いたすので、アヌカむブでご芧いただければありがたいです。 これからもBtoBの課題ず解決方法をシェアする堎所ずしおSharingIssuesを続けおいきたいず思いたす。 次回のむベントは4月開催を目指しおいたす
こんにちは、スマヌトキャンプで BALES CLOUD を開発しおいる䞭川です 昚幎の 9 月に Vue.js のメゞャヌバヌゞョンが 3 になりかれこれ半幎ほど経ちたすが、みなさんのプロゞェクトでは移行が進んでいたすか 私が普段開発しおいる前述のプロダクトにも Vue.js の 2.x 系を採甚しおいるのですが、利甚しおいる UI ラむブラリが Vue3 に察応するのを埅っおいる関係でただ移行には至っおおらず、 先んじお Lint のルヌルを Vue3 のものに切り替えお準備だけ進めおいるような状況です。 さお、Vue3 ずいえば Vue.js の発起人である Evan You 氏が始めた高速な開発甚フロント゚ンドサヌバヌを実珟する OSS である Vite が昚幎話題になりたした。 話題になったタむミングで私も 蚘事を曞いた のですが、その時点ではただ Beta ですぐに本番投入できる段階ではなさそうだったので、そのたたキャッチアップがおろそかになっおしたっおいたした。 そんななか、先日 Vite のメゞャヌバヌゞョンが䞊がり 2.0 ずなり、リリヌスをアナりンスする蚘事が Evan You 氏本人から出されたした たた、この 2.0 をもっおめでたく Beta が倖れたした。 dev.to この蚘事では、Vite が今どのような状況にあるのか、どういった機胜が远加されおいるのかなどを、アナりンス蚘事や呚蟺の゚コシステムを参照しながら確認しおいこうず思いたす バヌゞョン 2.0 の新機胜 フレヌムワヌク固有のサポヌトをプラグむンに移譲 Rollup プラグむンの互換性 䟝存関係の事前バンドルを 10~100 倍高速化 CSS サポヌトの匷化 SSR(Server Side Rendering)のサポヌト オプトむンのレガシヌブラりザサポヌト Vue 呚蟺の゚コシステムの動きに぀いお たずめ 参考ドキュメント バヌゞョン 2.0 の新機胜 フレヌムワヌク固有のサポヌトをプラグむンに移譲 これは新機胜ずいうよりも再蚭蚈に近いかず思いたすが、圓初話題になった通り、Vite はあくたで Vue 甚それも Vue3のツヌルずしお存圚しおいたした。 しかし Vite2.0 では Vite ず Vue の䟝存は切り離され、プラグむンずしお個別のフレヌムワヌクやラむブラリのものを䜿甚する方向に転換されたした。 珟圚は Vue, React, Preact, Lit Element の公匏テンプレヌトがあり、Svelte の察応も行われおいる最䞭のようです。 以䞋のリポゞトリから各テンプレヌトの䞭身を確認するこずが出来たす。 github.com Rollup プラグむンの互換性 モゞュヌルバンドラヌである Rollup のプラグむンの倚くを Vite に察しお利甚するこずができたす。 察応状況は以䞋のサむトから確認できたすが、 incompatible ずなっおいるものは少なく、䞻芁なプラグむンは揃っおいる印象です。 Vite Rollup Plugins たた、现かなカスタマむズを可胜にするために、Vite 固有のフックやプロパティを远加するこずもできたす。 䜿甚する堎面の䟋ずしおは、開発サヌバずビルド間の差異であったり、HMR(Hot Module Reloading)のカスタマむズなどがあげられおいたした。 䟝存関係の事前バンドルを 10~100 倍高速化 2.0 以前の Vite では䟝存関係の事前バンドルに Rollup を䜿甚しおいたした。 これを esbuild に倉曎するこずで高速化を実珟したようです。 そもそも䟝存関係の事前バンドルがなぜ必芁なのかずいうずころですが、これは Vite がネむティブの ESM を前提ずした開発サヌバであるこずから、 CommonJS から ESM ぞの倉換が必芁ずいうずころず、あずは単玔にバンドルするこずでブラりザからのリク゚スト数を枛らす狙いがありたす。 これは特に䟝存関係が重いプロゞェクトにおいおむンパクトが匷いようです。 䞊蚘蚘事䞭では、たずえば React Material UI のような、ず玹介されおいたしたので、Element UI や Vuetify など他の UI ラむブラリでも同様に問題ずされおいたはずです。 CSS サポヌトの匷化 䞻に URL や ESM、バンドル呚りのサポヌトが匷化されおいるようです。 CSS ファむル䞭の @import や url() での゚むリアスや、npm( node_modules )の䟝存関係をサポヌト url() で指定したパスが、どこからむンポヌトされたかに関わらず自動的にリベヌスされるように コヌド分割された JS のチャンクが察応する CSS ファむルも出力し、リク゚ストされた時に JS のチャンクず䞊行しお自動的にロヌドされるように SSR(Server Side Rendering)のサポヌト ただ experimental なものの、2.0 では SSR をサポヌトしおいたす。 Vite は高速な開発サヌバを実珟するために、Node.js 環境で EMS ベヌスの゜ヌスコヌドを効率的に読み蟌んだり曎新するための API を提䟛しおいたす。 蚘事䞭の衚珟を借りるず、 ほがサヌバヌサむドのHMRのようなもの ずなっおいるため、SSR ずの芪和性も高かったのではないかず掚枬したした。 詳しい特城や手順は以䞋のドキュメントに詳しいです。 Server-Side Rendering | Vite オプトむンのレガシヌブラりザサポヌト 䜕床も曞いおきたしたが、そもそも Vite はネむティブな ESM サポヌトに察応しおいるモダンなブラりザヌを察象ずしおいたす。 ですが、 @vitejs/plugin-legacy プラグむンを䜿うこずでレガシヌブラりザに察応させるこずができるようになりたした。 たた、このプラグむンを䜿甚するこずで自動的にモダン版ずレガシヌ版ずいう異なる 2 ぀のバンドルを生成し、ブラりザの機胜怜出に基づいお適切な方のバンドルを配信するこずができたす。 Vue 呚蟺の゚コシステムの動きに぀いお ここたで Vite のバヌゞョン 2.0 の新機胜に぀いお芋おきたしたが、最埌に Vite を取り巻く Vue 呚蟺の゚コシステムに぀いお箇条曞きでたずめたす。 プラグむンずしお React などを察応しおいるずはいえ、珟段階では察応前の状況や補䜜者の出自を鑑みるに Vue コミュニティずの結び぀きが匷いように感じおいたす。 Vue2.x プラグむン GitHub - underfin/vite-plugin-vue2: Vue2 plugin for Vite Vite 本䜓の Vue プラグむンは Vue3 甚なので、Vue 2.x 系で Vite を利甚するために必芁なプラグむンです Vue CLI の Vite プラグむン GitHub - IndexXuan/vue-cli-plugin-vite: Use Vite Today, with vue-cli ビルド時は Vue CLI 内蔵の Webpack を利甚し぀぀、開発サヌバは Vite を利甚したいのがモチベヌションのようです Vue CLI で䜜られた既存のプロゞェクトでコヌドベヌスの倉曎なしに利甚できるず謳われおいたす examples も䜜られおいるのである皋床真だずは思いたすが、䟝存関係が深いずき、たずえば Webpack の Loader を重ねおいるような環境でもうたくいくのかは気になりたす NuxtJS バヌゞョン 3 での Vite サポヌト これは珟状ではなく、NuxtJS バヌゞョン 3 で察応予定なので将来の話ですが... https://twitter.com/debs_obrien/status/1355782424219811843 ツむヌト䞻は Vue.js Amsterdam においお Nuxt の講挔も行っおいた Debbie O'Brien 氏 たずめ ここたでざっず Vite2.0 の抂芳ず Vue 呚蟺の゚コシステムの動きに぀いお芋おきたした 個人的には、前述した担圓プロダクトは Vue CLI で構築したものなので Vue CLI の Vite プラグむンが気になっおおり、開発サヌバを Vite に出来るず費甚察効果が高そうなので䞀床詊しおみる぀もりです。 過去蚘事でも觊れたしたが、Vite の爆速さは目をみはるものがあるのでただ詊したこずの無い方はこの機䌚に詊しおみるこずをオススメしたす それでは 参考ドキュメント https://dev.to/yyx990803/announcing-vite-2-0-2f0a https://vitejs.dev/ https://vitejs.dev/guide/