Conoha

ConoHa CLI 開発日誌 vol.8

  • POST
ConoHa-CLIの進捗報告。 まだまだやりたいことには届いてないから引き続き考えていくよ! 現状 Golangのパッケージに関して 複数環境のリリースに関して SSHに関して Golangのパッケージに関して Node.jsのrequireは1ファイル内でmodule.exportsに記載したものだけ返すが、 Golangのパッケージは1ディレクトリを1パッケージとして、全角英字で始まる関数やインスタンス等が全て返ってくる。 抽象化は1度しか行えないのでしっかりとオブジェクト指向的な設計が必要になる。 今回Go初挑戦ということで適当に作ったパッケージがあまり使い物にならないので見直す必要が出てきた。 現状の問題点としては、conf.Read()関数がconfigファイルを返す為、spec.tomlを操ろうと思ったらRead関数が使用済みの為に困ってしまう。 一旦はこの2つにリファクタリングしよう。 config endpoints 書籍を購入して勉強しているのだが、ディレクトリによるパッケージはサブディレクトリを切ればネスト出来るのでNode.js的な管理方法も十分可能に思える。 この辺を視野にいれて調査していこう。 参考サイト: パッケージについて - はじめてのGo言語 Go言語入門 複数環境のリリースに関して GitHubではタグを打った後、ファイルをアップロードすることでバイナリファイルをGitHub上に設置出来るらしい。 64bitのWindows、Mac、Linuxの3つくらいは上げておきたいから勉強必須。 ゆくゆくはMakefileかなんかで一撃でリリース出来るようにしたい。 参考サイト: Go のクロスコンパイル環境構築 - Qiita privateなGitHub Releaseページのリリース物をcurl+jqでダウンロードするワンライナー - Qiita GitHubのリリース機能を使う - Qiita Creating Releases - GitHub Help Release Your Software SSHに関して GolangにはSSHパッケージがデフォルトで用意されており、osの標準入力/出力につなげてやると簡単に実装出来るとのこと。 これによりWindows環境でも(多分)動作するSSHになりうる。 でもメインが電車によるSSH接続なのでMoshにも対応したいなあ。。。 というわけで、もう少し調査した後に再開という形になる。 参考サイト: Windows からも ssh でリモートコマンド実行したい、それ golang で出来るよ artyom/mosh - GitHub StanfordSNR/guardian-agent - GitHub

ConoHa CLI 開発日誌 vol.7

  • POST
ConoHa-CLIの進捗報告。 20連勤と毎日午前様のせいで全く進まないままアドベントカレンダー当日になってしまった… 結論から言うと、コピペコードでなんとか納めて公開したわけなんだが… 現状 infoサブコマンドの実装 imports を動的に生成 コピペコードで実装(苦 infoサブコマンドの実装 では早速作っていこう、 エンドポイントはこんな感じになるのかな。 var endpoints = map[string]string]{ "images": "https://image-service.tyo1.conoha.io/v2/images", "flavors": "https://compute.tyo1.conoha.io/v2/1864e71d2deb46f6b47526b69c65a45d/flavors", } …ってのっけからテナントID求めるのかよ。 ん〜…%sで引っ掛けてfmt.Sprintf使うか imports を動的に生成 Vim使いなのでシンタックスハイライト用にvim-goを入れていたが、 どうやらimportsを自動的に表現してくれるコマンドがあるらしいとのこと。 hnakamur/vim-go-tutorial-ja - GitHub インポートパスを手動で操作するのはとても 2010 年っぽい (訳注: 時代遅れ) です。この問題を扱うもっとよいツールを提供しています。もしまだ聞いたことがなければ それは goimports と呼ばれています。 私たちは :GoImports コマンド (最後の s に 注意) も用意しています。これで明示的に goimports を実行することができます。 これだね。 let g:go_fmt_command = "goimports" これ入れておけば自動的にやってくれるみたいだから入れておこう。 不要になったら削除までしてくれるらしいから完璧だね。 さて、早速実験。 fmt.printfn("hogehoge")で保存っと、よしよしちゃんとimport "fmt"になった。 じゃあconf.Read()を使ったらどうなるのっと…"github.com/miyabisun/conoha-cli/conf" 嘘だろ……!? これもバッチリ解決するとは恐ろしい…… もう私は長いGolang人生でimport文を自分で修正することは多分無い。 とはいえ、viperだけで”github.com/spf13/viper”を提示することは難しいと思うので、 この辺の依存関係をどう解決するかは今後も確認する必要がありそうだね。

ConoHa CLI 開発日誌 vol.6

  • POST
ConoHa-CLIの進捗報告。 今回も前回と同様に仕様回りを固める 現状 spec.tomlのフォーマットに関して instance.tomlは必要ないのではないかと考え直す conoha.tomlのフォーマットに関して spec.tomlのフォーマットに関して VM追加 - Compute API v2を元に最低限必要なものを見繕う instance_name_tag : インスタンス名 image: イメージ(UUID) flavor: VMプラン(UUID) user_data: cloud-config (URL or ./cloud.cfg) key_name: SSHキー名 おっ、最小で考えたら意外と少なくいけるな。 ユーザースクリプトがAPI越しだとcloud-configオンリーなのが悲しい。 ところで、考えないようにしてたけどこのイメージとVMプランのUUIDとはなんぞや? イメージ一覧画面を見たが何も書いて無かったので、 VM追加 - Compute API v2のページから推測しよう。 Request Json (最低指定時) { "server": { "imageRef": "1f7bcc63-4a18-4371-85b1-bcdd4301ff31", "flavorRef": "b60acd11-3fd5-46e1-9387-aae4737d49aa", "adminPass":"72LY2hf38Kf84vCy4sUr" } } ハイフンでセパレートされた4-2-2-2-6バイトの文字列がそれっぽいな。 どれどれ、この情報を踏まえてイメージ一覧を。。 イメージ一覧取得(nova) - Compute API v2 images[n].nameの他にimages[n].idがあって、このidがUUIDの形式に一致することがわかる。 { "images": [ { "id": "fb1d084f-357f-40e2-a2c3-59b8ecc1f6f2", "links": [{link}, {link}, {link}], "name": "vmi-centos-7.

ConoHa CLI 開発日誌 vol.5

  • POST
ConoHa-CLIの進捗報告。 個々の所午前様ばかりで全然作業が進まない。 今回はしっかり時間を作ってどう作って行くかを考えていきたい。 現状 ConoHaのゴールに関して カレントディレクトリのファイル仕様 コマンド一覧(予定) ConoHaのゴールに関して 前回考えたConoHaのゴールに関して、vagrant sshコマンドが再現出来れば良い事はわかっている。 諦める前に一回確認しておこう、というわけでGitHubに公開されているソースコードを閲覧してみた。 該当するスクリプトはこの辺にありそうだ。 vagrant/lib/vagrant/action/builtin/ssh_exec.rb vagrant/lib/vagrant/action/builtin/ssh_run.rb vagrant/lib/vagrant/util/ssh.rb まぁ、Rubyのコードをあまり読めないから大変なんだが、どうやらvagrant/action/ssh_run.rbを読む限り、具体的な処理はutil/ssh.rbに移譲しているようだ。 うーむ、やはりサブプロセスで動作させて、インタラクティブな状態で紐付けているようだ。 しかしこれでSSHで繋いだ先でVimやtmuxを平然と使えるって凄いな。 なんとなくできそうな事はわかったが、Goだとどうやって実装すればいいんだ。 How can I open an interactive subprogram from within a go program? josephspurrier/sshclient.go - GitHub Gist ん?なんかめっちゃ簡単な事書いてないか? cmd := exec.Command("ssh", option) cmd.Stdout = os.Stdout cmd.Stdin = os.Stdin cmd.Stderr = os.Stderr cmd.Run() まさかこれだけでいける? オプションのあたりは作り込む必要がありそうだけど、一応覚えておこう。 既存sshと連携したければvagrantと同じくconoha ssh-configで表示されるようにしたい。 カレントディレクトリのファイル仕様 spec.toml: 仕様(名前, OS, ssh-key, インスタンスタイプ…などなど) instance.toml: ConoHaのインスタンスの情報 1ディレクトリ、1設定ファイル、1インスタンス。 これもvagrantにある程度合わせる形で考えた。

ConoHa CLI 開発日誌 vol.4

  • POST
ConoHa-CLIの進捗報告。 チラ裏成分多め。 車駆動開発だとGoの依存ライブラリを落とすだけで世界が止まる。 早くConoHa環境でオラオラ作業したいわぁ。 現状 切り出したログイン処理のリファクタリング コンパイルエラーとの戦い Windows用のホームディレクトリの調整 Glideはオワコン ゴールをどうするか悩む 切り出したログイン処理のリファクタリング 切り出したログイン処理が汚いが諦めて布団に潜った所、 翌日の朝に閃いてリファクタリング、まだまだ拙いが良い感じの粒度で切り出せたように思える。 コンパイルエラーとの戦い single-value contextというエラーが出て中々解消出来ない。 とりあえず色々ググっていたら、戻り値が2個のものを1個だけ受け取っていた事が原因らしい。 不要の場合でも_で受け取る必要があるのね。 全部のコンパイルが通ってログインが通った所で一旦コミットしてGitHubへプッシュ。 Go言語の気に入ったところ/気に入らなかったところ Windows用のホームディレクトリの調整 viperは$HOMEというパワーワードをよしなに解釈してくれるので問題なさそうだが、 コンフィグファイルを読み書きしている箇所はosパッケージを利用しているので、 Windows環境では恐らくコンフィグファイルを読み書き出来ない不具合が登場しそう。 go-homedirというパッケージを用意して読み書きに対応する まずGitHubのプロジェクトルートへジャンプ! うわ、ReadmeにUsageないじゃんピンチ! あ、でも英語読めば十分理解出来る。 一応関数の使い方を確認しておきたいのでgolang go-homedirでぐぐったらGoDocなるサイトが引っかかって理解出来た。 念のためプロジェクトのhomedir.goも確認、たったの100行じゃん楽勝。 確かにDirは引数無しのstring, errを返すし、Expandはstringを受け取りstring, errを返す。 $ glide get github.com/mitchellh/go-homedir Golang で filepath.Abs に ~(ホームディレクトリ) を指定した時にカレントワーキングディレクトリが先頭についてしまう package homedir - GoDoc Glideはオワコン Glideで入れたgo-homedirが使えないので使い方の確認を兼ねて探していたら、 Glide から dep に移行せよ - Qiita の記事でdepに移行せよとか煽られてる この間教えて貰ったばっかりなのに! いやまだわからん、公式で確認しておこう。 GlideのGitHubプロジェクトルートへ行ってみると…… Golang Dep The Go community now has the dep project to manage dependencies.

ConoHa CLI 開発日誌 vol.3

  • POST
ConoHa-CLIの進捗報告。 まだちゃんと全てを切り出せたわけではないが、 現状 ログイン処理の外出し 時刻の比較 ログインの再実行 ログイン処理の外出し ログインコマンドは出来上がった。 ConoHaのAPIへ接続し、TokenIdを持ち帰り~/.config/conoha.tomlに吐き出せるようになった。 しかし、このTokenIdはわずか1日しか有効期限がない上、APIの殆どはTokenIdを求めてくる。 現状の作りでは日付を跨ぐ度にTokenIdの有効期限が切れていますエラーを食らい、 その度にログインコマンドを打ち込む作業が待っている。 ログイン処理を抽象化して取り出す必要がある。 早速プロジェクトルートにutilというディレクトリを作成した。 (ベストプラクティスはまだ良くわかっていないが、公開して有識者の目に止まればPRでも貰えるだろう) Go言語でエラーを書くときに気をつけること - taknb2nchのメモ Go言語でパッケージの修飾名が重複した場合の対応方法 - taknb2nchのメモ 時刻の比較 まずは時刻。 トークン時刻が期限切れか否かを確かめる方法がよく分からない。 Time同士の比較はないのか? 一度Unixタイムに変換して数値同士で比較するように修正した。 Package time Go言語で時刻を - そこはかとなく書くよん。 逆引きGolang (日付と時刻) How to convert ISO 8601 time in golang? ログインの再実行 トークンが古ければもう一度ログインを試みて取得しなおすように修正。 Golangだと処理的になってしまうなぁ……色々とださいがまぁまぁええわ。 動くの大事。 最低限体裁を整えたので一度完了として次へ Next… Mac以外のHomedirectoryも取得出来るようにしたい Golang で filepath.Abs に ~(ホームディレクトリ) を指定した時にカレントワーキングディレクトリが先頭についてしまう package homedir

ConoHa CLI 開発日誌 vol.2

  • POST
今日のConoHa-CLIの進捗報告。 ConoHa-CLIの報告だと、上司はこのはちゃんになるのだろうか? 現状 標準入力からの値取得 ConoHaのAPIを叩いてログイン(トークンID取得) トークン情報を引き出す TOMLファイルを更新 標準入力からの値取得 現在loginコマンドを実装中。 オプションでID、Password、テナントIDを入力させる作りにはしたが、 入力項目が足りない場合は標準入力から煽って入力させる作りを目指した。 参考サイト: flag パッケージ - golang.jp Go 言語で標準入力から読み込む競技プログラミングのアレ — 改訂第二版 早速参考サイトを元に実装を行う。 優先順位の要件は下記。 コマンドライン引数-tからの入力値 $HOME/.conohaの設定項目 標準入力と標準出力で入力させる まずはcmd/root.goでcobraとviperの設定を行う func init() { cobra.OnInitialize(initConfig) RootCmd.AddCommand(versionCmd) } func initConfig() { viper.AddConfigPath("$HOME") viper.SetConfigName(".conoha") viper.SetConfigType("toml") viper.ReadInConfig() } 次にcmd/login.goで各種値を取得するように設定を行う。 func init() { rootcmd.addcommand(logincmd) logincmd.flags().stringp("tenantid", "t", "", "port to run application server on") viper.bindpflag("auth.tenantid", logincmd.flags().lookup("tenantid")) } var loginCmd = &cobra.Command{ Use: "login", Short: "Calculator of addition.

ConoHa CLI 開発日誌 vol.1

  • POST
Go言語でConoHa-CLIを作成しているので、 少しずつ進捗報告をしていきたい。 現状 Glideを導入 cobra / viperを導入 TOMLを導入 構造体の外出しでハマる Glideを導入 Glideはパッケージ管理ソフト。 先日参加したGoビギナーズLT大会! 「最近、Go言語始めました」の会 #4というイベントで、 Go言語のパッケージ管理はGlideを使うのが筋が良いと聞いて導入を決意。 参考サイト: Goビギナーズ - よくある3つの質問 - mom0tomo go getはローカルマシンに落としてしまうのでパッケージ管理というレベルじゃねーぞ状態だったが、 Glodeではプロジェクトルートに設定ファイル、vendorディレクトリに依存ライブラリが次々と担ぎ込まれ、 npmとほぼ同じ使用感で使う事が出来た。 ただ、LT大会を聞いている限り、Glideを使って入れたらハマったので結局go getでやりました。 使い方教えてという悲痛な声だらけだったので、酷いハマリポイントがあるんだろうなぁ(白目 cobra / viperを導入 cobraはCLI用のライブラリ。 Node.jsに於けるCommander.jsみたいなもん。 Commander.jsはサブコマンドの実装で大ハマリしたが、cobraはわりと素直な動作だしドキュメントが充実してて書きやすい。 お供はviper、蛇繋がりか。 こちらはJSON、YAML、TOML等の設定ファイルをよしなに展開してくれる。 また、cobraとの共存も見越しており、オプション設定にフックしてよしなに上書きすることも可能。 なにそれ便利過ぎィ! ただし、環境変数や複数の設定ファイル読み込み、オプションのオーバーライド等の兼ね合いから、 ファイルへの書き込みはサポートしていない模様。 (なんかファイルに書き出したいという要望がプルリクに上がってて、マージされてるっぽいんだけど、masterにはないもよう) ファイルへ吐き出す場合は、別途何かしらのライブラリを用意してきて勝手に出力するしかない。 ただまぁ、viperから最新の値を抜き出して上書き出来るから全くのゼロスタートというわけではないかな。 TOMLを導入 TOMLとはGitHubの人が提唱している設定ファイル。 IniとJSONの良いとこ取りといった感じ、インデント無しで配列やオブジェクトを宣言出来るため、ネスト地獄が起こらないのが主張。 最初はYAMLで書いてたのだが、どうもTOMLの方が便利そうなのでそちらを利用することに。 構造体の外出しでハマる コンフィグファイルまわりは外出ししようとプロジェクトルートにはconfというディレクトリを作成して外出し。 どうしたものか、conf.auth = xxxがundefinedですとコンパイル通さなくなった。 しかしここはさすがのQiitaクオリティ、同じネタでハマった人を発見して無事解決。 参考サイト: Goの構造体をpackageに外出ししてハマッたこと

【ConoHa】APIからデフォルトのイメージ一覧を取得する

  • POST
※本投稿は調査段階のメモ書きです 何処で取れるのか? イメージ一覧取得(nova) - Compute Service https://www.conoha.jp/docs/compute-get_images_list.html ログインしてトークンを受け取っていないと使えない ログインしなくてもアクセス出来そうな情報ではあるのだが… $ curl https://compute.tyo1.conoha.io/v2/1864e71d2deb46f6b47526b69c65a45d/images Authentication required 今やろうとしてること 仕事であちこちのブランチをちょこちょこ弄るのに苦戦中。 これを解決するために、ConoHaのインスタンスを複数作って臨機応変に対応出来るようにしたい。 利用予定の技術 これらを駆使してインスタンスを好きな時に生やせる仕組みを作る BitBucket ConoHa API Vagrant Ansible 進捗 VagrantでConoHaのインスタンスを作成する際、正確なプラン名、イメージ名が必要になる。 しかし、公式のAPIを眺めても理解出来なかったので、結局ググッて他のサイトからどのAPIが該当するのか調べる事になった。 というのも、イメージと一言に言っても今回の目的であるテンプレートのイメージの他に、ユーザーが登録したISOイメージ、スナップショット等がありどれが対象かは一目で分かりづらい。 最終的にはコマンドラインツール化等もしていきたいので、手早くしないとね…