TRY AND ERRΦR

気になったこと、勉強したこと、その他雑記など色々メモしていきます。。Sometimes these posts will be written in English.,

AWS セッションマネージャーでセッション20分制限を回避

AWS セッションマネージャーを使うとIAMユーザーでEC2にログインできるようになります。
(正確にはログインではないのですが。。)

ただ1つ問題があって、何もしない状態が20分続くとセッションが強制的に終了してしまいます。

ユーザーのアクティビティがない場合、20 分後にセッションは終了します。

セッションを終了する - AWS Systems Manager


何もしない状態(=ユーザーのアクティビティがない場合)が20分というのは、ssh繋いだまま昼飯行って放置したりする場合はもちろん、プログラム実行中で放置せざるを得ない場合なども含まれるので、今までのsshの代替として使うのはちょっと厳しいなあと思っていました。

が、この20分の制限を回避する方法がありました。


まず、セッションマネージャーでEC2インスタンスに接続する方法としては、
1) AWSマネジメントコンソール上からブラウザベースのCLIクライアントを使って接続する
2) ローカルのターミナルからSSHクライアントを通じてProxyCommandで接続する
の2つがあります。

1)を使う場合は回避できませんが、2)では以下の設定を追加することで回避できます。

# ~/.ssh/config
# デフォルト以外の名前付きプロファイルを使っている場合、--profile [プロファイル名] で指定する
host i-* mi-*
    ProxyCommand sh -c "aws ssm start-session --target %h --document-name AWS-StartSSHSession 

# ↓ これを追加
ServerAliveInterval 60


ServerAliveIntervalは指定した期間(秒)にサーバーからの応答がない場合に、応答確認をサーバーに送信するというパラメータですが、これを設定することで応答確認のpingがアクティビティと見なされるため、セッションが維持されるようです。

【Vue】CORS環境でaxiosでレスポンスヘッダが足りない時

CORSの場合、API側で色々詰めてるはずのレスポンスヘッダをダンプするとContent-Typeしか返ってこない。。
というかブラウザの開発コンソールのネットワークタブなどで見ると実際には返ってきているが、console.logでダンプした時には除去されている。
どうやらブラウザではデフォで以下のヘッダーしか見せないようにしているそうです。


Cache-Control
Content-Language
Content-Type
Expires
Last-Modified
Pragma


サーバ側でAccess-Control-Expose-Headersヘッダをつけると、ここで指定したヘッダをjsで取れるようになります。

Access-Control-Expose-Headers: YourCustomHeaderName1, YourCustomHeaderName2



In the case of CORS, you seems to get headers only like below even if you set something other stuff on the server side.But actually you can see other headers which is correctly passed on the network tabs of developer console.
Why is that?
The reason is that browser permits you to access headers just only following fields by default. If you get other headers you could put 'Access-Control-Expose-Headers' on the server side and you explictly set your header fieldname in it.

Goでsclevine/agoutiを使ってページ全体をキャプチャする方法

ページの内容によってagouti.Pageのwindowサイズを変えて内容全体が写るようにキャプチャしたい場合、
RunScriptでbodyのサイズをとるjavascriptを実行 -> ページ毎にSize()で指定すれば綺麗にフルスクリーンキャプチャがとれます。
(省略してますが、ChromeDriver使ってます。)

type MyPage struct {
	*agouti.Page
}


/*
 * Take screenshot
 *
 */
func (mypage *MyPage) SS(filename string) {
	var width, height int
	mypage.RunScript("return document.body.scrollHeight;", nil, &height)
	mypage.RunScript("return document.body.scrollWidth;", nil, &width)
	mypage.Size(width, height)
	mypage.Screenshot(filename)
}

PHPのFacebookWebdriverでも確かexecuteScriptみたいなメソッドあったので、同じ感じでいけるかも。

Trap on findElement with cssSelector for Facebook WebDriver

github.com


In my case using Facebook WebDriver for Headless browser Testing, there is a trap on findElement with cssSelector.
Assume you want to find the element(s) by css selector that you specify like what their style attribute doesn't have "display:none",
for example you would use WebDriverBy::cssSelector like below.

Facebook WebDriverをテストで使っていて、その時にcssSelectorを使ってfindElementする際のトラップの話。
style属性にdisplay:noneを含まない要素を取得する際、WebDriverBy::cssSelectorでこんな感じに書ける。(部分一致的なやつです)

WebDriverBy::cssSelector("ul li:not([style*='display:none'])")


Although above aims to specify "li" which is visible element located in "ul", you cannot find them if they have half space between "display" and "none". In this case
you have to do insert a half space in the selector like this.

上記はulの中で可視化されているliを特定するためのものだが、displayとnoneの間に半角スペースがあると特定できない、、、
この場合、以下のようにcss selectorに半角スペースを入れる必要がある。

WebDriverBy::cssSelector("ul li:not([style*='display: none'])")

Besides I tried to use ":visible" selector for WebDriverBy::cssSelector(), but It didn't work with log "invalid selector ~".

また、:visibleセレクターも試したけどinvalid selector~~と言われてダメでした。。

今更ながらphpでword(docx)を読み込んでplain textを得る

word(docx)ファイルを出力する、とかのサンプルやライブラリは結構あるんですが、
今回はそもそもただ単に中身のプレーンテキストが欲しいという場合の話。

docx(確かword2007以降)は実はzipアーカイブなので、unzipとかで解凍できる。
その中にword/document.xmlというのがあって、それにテキストの情報が入っている。
これをパースしてパラグラフ -> テキストで回せば改行含めプレーンテキストとして取得できます。

今回はPHPのZipArchiveでパースしますが、別にphpでなくても全然大丈夫です。
PHP: ZipArchive - Manual

$NL = "\n";
$contents = "";
$file_path = "your.docx";
$zip = new \ZipArchive();

if ($zip->open($file_path) === true) {
	$xml = $zip->getFromName("word/document.xml");
	if ($xml) {
		$dom = new \DOMDocument();
		$dom->loadXML($xml);
		$paragraphs = $dom->getElementsByTagName("p");
		foreach ($paragraphs as $p) {
			$texts = $p->getElementsByTagName("t");
			foreach ($texts as $t) {
				$contents .= $t->nodeValue;
			}
                        // Add New Line after a paragraph.
			$contents .= $NL;
		}
	}
}
return $contents;
English sub


Although There are many samples and libraries on the web, this post is about that simple way you can get the plain text from docx file.
docx file is essentially zip archive that consists some rels, So we could unzip it.
there is a xml file named document.xml in the rels which has information of text.
We could fetch plain text by parsing xml and iterating its specific node which are like paragraph or text,,

CodeDeployでALB-EC2へのデプロイ時間を短縮する

AWS CodeDeployでALB配下のEC2にインプレースデプロイする際、本番にデプロイした際にいきなり遅くなった、、、


結論、本番のALBターゲットのヘルスチェック間隔がdevのそれよりも長かったのが原因でした。


以下のフォーラムによると、デプロイ時にトラフィックを止める際、ヘルスチェックの設定に依存するとのことなので、
デプロイする時だけヘルスチェックの間隔を短くするとかなり速くなります。

https://forums.aws.amazon.com/thread.jspa?threadID=254752


ちなみに、今回は間隔を30秒 -> 5秒(最小の閾値)に、さらに間隔に付随するタイムアウトなどの設定も合わせて変更したところ、
デプロイ時間が半分以下になりましたw