2014年2月27日木曜日

USBメモリを暗号化してデータ保管できる「TrueCrypt」

http://www.truecrypt.org/

USBメモリを、暗号化して持ち出すことができるアプリケーションです。
英語版ですが、別途言語ファイルを追加する事により日本語化も可能です。


USBに関して、実現できる方法は2通り。

1) USBメモリそのものを暗号化
2) USBメモリに、暗号化されたファイル(コンテナ)を作成し、その中にデータを格納

1)のケースは、持出先でもTrueCryptのアプリが必要であり、今回は
不特定多数の環境でもデータを見る必要があることから、2)を採用。

インストール手順

1) ソフトをダウンロード
2) インストーラを起動
3) 選択肢の中で、「Extract」を選択。展開先としてUSBを選択(フォルダは任意)
  これにより、持ち運び可能なアプリとして展開されます。
4) 進めていくと、USBへの展開が完了。
5) 言語ファイルを、上記で展開したフォルダへコピー

ここまでで、利用準備が完了です。

暗号化データの作成

アプリ[TrueCrypt Format.exe]を利用します

1) 暗号化されたファイルコンテナを作成 を選択
2) 「TrueCrypt標準ボリューム」を選択
  もう一つの選択肢は、暗号化ファイルの中に暗号化ファイルを含む。というような動作です
3) ボリュームの位置にて、USBメモリ内の、任意のパス、ファイル名を指定
  私の場合、一見わからないファイル名にしています
4) サイズ
  コンテナのサイズです。後に、これが、暗号化ドライブの容量となります。
5) パスワード
  ご自由に
6) ボリュームのフォーマット
  適度にマウスを動かしたのち、「フォーマット」
  ドライブ容量にもよると思いますが、そこそこ待ちます。

これで、暗号化したいデータを格納できるコンテナファイルが完成です。


暗号化ドライブの利用

1) TrueCrypt.exeを起動
2) 一覧より「ドライブ」を選択
3)「ボリューム」の欄で、先ほど作成したふぃあるを選択
4) パスワードを入力

これで、ドライブとして認識されます。


使い終わる際には、マウントを解除してから、USBをを取り外すのが確実です。

2014年2月25日火曜日

findとlocate (linux)

ふと気になったのでまとめ。(というか、あまり知らずに使っていました)

locate 【ファイル名(ファイル名の一部)】

ファイルリストをインデックス化し、インデックスを検索します。
インデックスファイル(slocate.db)が更新されていないと、古い検索結果がヒットします。


find / -name 【ファイル名】

ディスクを検索します。全件検索のためlocateよりは時間がかかります。


locateで使用しているインデックスファイルを更新するためには以下のコマンド

updatedb


インデックスは、ディストリビューションによってはcron.dailyで自動更新するように
設定されているようで、CentOS 6.4の場合、[makewhatis.cron]というものが
動いて、自動更新されるようです。


2014年2月24日月曜日

メーリングリストで「Loop Alert: Duplicated Message-ID」が返される

いつの間にか、件名に「Loop Alert: Duplicated Message-ID」という内容が付加された
メールが届くようになりました。

サーバーの運用管理を行っているため、定期的にメールが飛んでくるのですが、
いつからか、同じメールが複数通。そのうちの1通についてきます。


これが出るようになってからは、付加情報はついてくるわ、
毎日倍のメールを受信する事になってしまうわ。ということで、
運用に支障が出てました。


結局のところ、メーリングリストと、メール転送のループという事が判明。

どういうことかというと

メーリングリスト:server-admin-ml@domain
参加者:server-admin@domain
server-admin@domainは転送メールで、転送先が、server-admin-ml@domain


つまり、server-admin@domainのメールアカウントを経由して、2通送られたというわけ。

一部サイトにはメーリングリストソフトの動作が原因というのがあって
どうしようかなと思っていたのですが、原因単純で助かりました。

2014年2月21日金曜日

sedでファイルの特定行の文字を置き換える

同じような環境をいくつも作ると、手順化、sh化することが出てきます。

そんななか、各種インストールの後に行うconfの設定作業は
手作業の中でも間違うと危険な分類のため、できるだけ自動化したいところです。


今回、zabbixのAgent構築で使った使用例を纏めておきます。

※confの形はバージョン依存でもあるので、頻繁にconfが変わるアプリを使う場合にはご注意ください。

実施例

#ディレクトリ移動
cd /etc/zabbix/

#念のためバックアップ
cp zabbix_agentd.conf zabbix_agentd.conf.default

#ServerNameを、指定したサーバーへ置き換える
sed -i -e 's/Server=127.0.0.1/Server=zabbix-server.domainname.com/' zabbix-agentd.conf

#ServerActiveを置き換える
sed -i -e 's/# ServerActive=/# ServerActive=\nServerActive=zabbix-server.domainname.com/' zabbix-agentd.conf



#自分を宣言する #$HOSTNAMEはサブドメインが入っている変数

sed -i -e 's/Hostname=Zabbix server/Hostname='$HOSTNAME'.domainname.com/' zabbix-agentd.conf




変更点を目視で確認

diff zabbix_agentd.conf zabbix_agentd.conf.default


2014年2月19日水曜日

小数点を持つ値の計算で誤差が生まれる件(JavaScript)

今更・・・という話ですが、とあるシステムでの不具合にて、原因を調査していたところ発覚。

小数点がある数値を含む計算を行った際に、計算結果が合わないという事が起きます。


理由としては、JavaScriptの演算はIEEE 754という規格に従って実装されているという事。
仕様であり、JavaScript的には正しい値なので避けようがありません。


ちなみに、以下のような演算でも誤差が起きます。

(17.955 * 100000) = 1795499.9999999998


原理や理屈は「演算誤差」などで調べてもらうとして、利用するソフトウェアによっては発生しうる現象です。


今回のケースでは、金額の計算だったため、コンピューターの都合による誤差は認められません。。。。

対処法

「いったん整数に変換してから演算して戻す」などがよくありがちですが、
JavaScriptだとそこそこの行数でロジックを書かなければだめそうなので
こちらは別途纏めたいと思います。


追伸

net framework(vb.net)でも同じ結果となりました。こちらは、小数点の値に対して、[Decimal]を明示する事で対処できそうです。

(Convert.ToDecimal(17.955) * 100000) = 179500D

Javaでも起きますね。こちらはBigDecimal型を使って計算すれば対処できます。


2014年2月18日火曜日

クロスブラウザテストができるサービス(BrowserStack)の無償期間が終わっていた

以前、ブラウザ上からクロスブラウザテストが簡単にできるサービスをご紹介しましたが、
いつの間にやら、無償サービスの期間が終わってしまっていました。

その時の記事はこちらをご覧ください。
http://knkryo.blogspot.jp/2013/11/web.html

使い続けるには、有償サービスへの移行が必要

今のところそこまでの使用頻度はなさそうなので、modern.ieより
都度、仮想環境をダウンロードして使う事になりそうです。


ツールのダウンロードはこちらから
http://loc.modern.ie/en-us/virtualization-tools

2014年2月17日月曜日

BloggerでGoogleAnalytics

Bloggerには標準でアクセス解析がついていますが、シンプルなもので
詳しい解析の機能がなかったため、GoogleAnalyticsを使う事にしました。

どちらもgoogleサービスなので、手順は簡単です。

手順

1) Google Analyticsアカウントを取得、設定

以下サイトから、「ログイン」または「アカウントを作成」で入ります。

Analytics設定から、「アカウントを作成」することで、トラッキングIDを取得します。

詳しくはGoogleのサポートにも記載されています。
https://support.google.com/analytics/answer/1032385


2) Bloggerで設定

設定で、先ほど取得しているトラッキングIDを設定します。
https://support.google.com/analytics/answer/1009610?hl=ja


ひとまず仕込み完了したので、しばらく様子を見たいと思います。


2014年2月13日木曜日

Excelで保護されたセルに色を付ける

Excelでセルの保護を使うことがありますが、あちこちに設定していると
ぱっと見で確認したいケースが出てきます。

1行Tipsですが、忘れた時のためにとっておきます。

手順

1) 条件付き書式を使用します。
2) 「数式を使用して、書式設定するセルを決定」を使用します。
3) 条件に、以下を入力し、書式で背景色などを設定します。
 =cell("protect",a1)=1
 ※開始位置が「a1」でない場合には適宜書き換えてください。

なんだかんだ言ってExcelって最強のフロントエンドツールだったりすることを最近つくづく感じます。

2014年2月12日水曜日

Excelで単一行と複数行のシートをセル参照で解決する

イメージ的には以下のような感じです。


元々1行のものを、複数行の表で参照しようとした場合、
「=表!C3」 というような表現だと、単純に参照設定を作ることができません。

1行が1行として参照するのであれば、一つ参照をつくって、コピーすれば済みますが、
複数の場合、どうやっても単純コピーではいきません。



そこで、調べてみたところ、別アプローチでの解決方法がありました。

キーワード

OFFSET ・・・ 指定した参照から指定した行数、列数の範囲への参照を返します。
ROW()  ・・・   参照の行番号を返します
COLUMN() ・・・ 参照の列番号を返します。

理屈

OFFSETで、相対位置を指定する事により、任意の場所の値が取れます。
ROW()とCOLUMNを利用して、スタート位置からの相対を指定します。


実践

別シートに分かれているものとします。
2行構成のシートから、1行校正のシートを参照します。

・行Noを取得する (行Noは、A列2行目に1行目がある)
 =OFFSET(表!$A$2,((ROW())-2)/2,0)
 ※解説
  ・表A2からスタートで、相対位置(行)を計算、列はそのまま。
  ・1行目の相対位置は、$2から見るとゼロ。ROW()-2/2もゼロ。よってそのままの行
  ・2行目はとなると、ROW()が4なので、(4-2)/2 でイチ。$A$2から行がプラスイチなので、3

相対位置のスタートを絶対指定にするのがポイントです。
これで、同じ計算式を使いまわすことが可能です。

ちなみに、名称の欄には
 =OFFSET(表!$B$2,((ROW())-2)/2,0)
と指定しています。


きちんと使うなら、
=IF(OFFSET(表!$A$2,((ROW())-2)/2,0)="","",OFFSET(表!$A$2,((ROW())-2)/2,0))

とやると、きれいにいくかもしれません。

2014年2月10日月曜日

インストール不要。簡単なデスクトップ共有 screenleap

リモートデスクトップのツールのなかで、インストール不要。複数人が
同じ画面を見れるようにできるツールがscreenleapです。

見せたいPCに、JRE(JavaRuntime)さえインストールされていれば
見る側は、ブラウザだけでOKです。

見せる側の手順

1.サイトにアクセス [http://www.screenleap.com/]
2.[share your screen now]をクリック
3.Javaの実行確認画面が出るので、[OK]をクリック
 ⇒出ない場合には、Troubleshootingの説明に従い、JAVAをインストール
  ※インストール後にはブラウザの再起動が必要です。
4.Javaを実行してよいかという確認画面が出るので、[OK]
5.URLが出るので、見せたい人へ送る。

見たい側の手順

1.伝えられたURLをブラウザで開く


余談

見せる側のブラウザがIE6だとJAVAのプラグインが開きませんでした。
そのような場合には、Firefoxなどをお使いください。

2014年2月7日金曜日

Webテストを自動化 Selenium

Webシステムの開発で、テストの自動化ツールを見つけたので、
導入からファーストタッチまでを纏めておきます。

ツールについては@ITさんにて記事が公開されています。
http://www.atmarkit.co.jp/ait/articles/0908/19/news109.html


概略

1.画面で操作している内容を記録でき、再現できる。
2.実行環境が異なっても可。

インストール

1.Mozilla Firefox のアドオンとして、Selenium IDEをダウンロード、インストール。
2.Firefoxのメニューバーより「ツール」を選択し、「Selenium IDE」を選択。(またはControl+Alt+S)

以下の画面が開きます。


実行

ウインドウ右上の赤丸で記録開始終了、記録を開始すると、一覧に内容が追加されていきます。
一覧の上にある三角マークで実行開始、終了。一括でも、一つずつでもできるようです。

作成したテストケースは保存でき、他の人が開く事も可能。

ひとまず使ってみて、追って追加情報を更新したいと思います。

2014年2月6日木曜日

複数のデスクトップ環境を構築できる dexpot

百聞は一見に如かず。

dexpot

個人利用に限り、無償利用が可能です。
標準は英語版、日本語化に対応してくださっている方もいるので、
日本語で利用可能です。


主だった機能

・ホットキーで、デスクトップの切り替えができる
・デスクトップごとに、背景画像などの設定が返られる
・デスクトップマネージャ 機能により、ワンクリックでウインドウを切替可


常日頃、画面を出す、しまうという動作を繰り返しで身についてしまっているので
これを使いこなせるようになれば、日常が大幅に変わってきそうです。



追記: 使ってみたところの主要ポイント

●デスクトップごとにアイコンの指定が可能。
 用途で分ける事を考えているので、これはベストマッチ。デスクトップを見るだけで何のデスクトップ化がすぐにわかるようになります。

●アプリケーションごとに起動するデスクトップを指定可能
複数デスクトップで利用している時に、dexpotを終了すると、全てのデスクトップのアプリは元の画面へ戻ってきます。
言い換えると、その逆ができる。ということで、
「アプリケーションを割り当てる」という設定から、該当のアプリを選択。

使い方を誤ると若干びっくりしそうな機能ですが、用途別ではっきりしている時には便利そうです


●自動でアプリケーションを起動
指定したプログラムが自動的に起動するようになります。
「デスクトップごとの設定」より、「スタートアップ」を選択して指定。

アイコンが出てこなくなった時には、デスクトップを右クリックして、「表示」から「デスクトップアイコンを表示」を選択

2014年2月5日水曜日

vb.netでキーボードHook

仕事で開発・保守をしているシステムで、モジュール提供されている部品に不具合があり、
どうしても回避しないといけなかったので、Hookにて対処する事にしました。

現象としては、「ある特定の項目にフォーカスがある際に、F3を押すとゼロ除算エラー」
モジュール側の不具合であることは調査により発覚。しかし、モジュールは直せない。

ということで、HookにてF3を拾って、潰すというロジックです。

いろいろ調べていると、".net framework"ではグローバルフックができず、マウス、キーボードのみ。とか書いてはありましたが、APIを使えるのでさほど気にもならないかなと思ってます。

とはいえ、Hookは低レベル(OSに近い部分)での制御になりますので、使い方には十分ご注意ください。
何の処理でもCancelなんてしようものなら、全ての入力を受け付けなくなってしまう事もあり得ます。

ソース

クラスライブラリ側


・APIを直接フックを実施
・フックにより取得できるメッセージの中からキーコードを取得
・イベントとして外部へ公開


Imports System.Runtime.InteropServices

''' <summary>
''' キーボードフックを行うライブラリ
''' </summary>
Public Class KeyboardHook
  Implements IDisposable

  Dim WH_KEYBOARD_LL As Integer = 13
  Private Shared hHook As Integer = 0

  Private hookproc As CallBack

  Public Event KeyboardEvents(ByVal sender As Object, ByVal e As System.Windows.Forms.KeyEventArgs)

  Public Delegate Function CallBack( _
    ByVal nCode As Integer, _
    ByVal wParam As IntPtr, _
    ByVal lParam As IntPtr) As Integer

#Region "DLL Declare"

  'Import for the SetWindowsHookEx function.
  <DllImport("User32.dll", CharSet:=CharSet.Auto, CallingConvention:=CallingConvention.StdCall)> _
   Public Overloads Shared Function SetWindowsHookEx _
     (ByVal idHook As Integer, ByVal HookProc As CallBack, _
      ByVal hInstance As IntPtr, ByVal wParam As Integer) As Integer
  End Function

  'Import for the GetModuleHandle function.
  <DllImport("kernel32.dll", CharSet:=CharSet.Auto, CallingConvention:=CallingConvention.StdCall)> _
   Public Overloads Shared Function GetModuleHandle _
      (ByVal lpModuleName As String) As IntPtr
  End Function

  'Import for the CallNextHookEx function.
  <DllImport("User32.dll", CharSet:=CharSet.Auto, CallingConvention:=CallingConvention.StdCall)> _
   Public Overloads Shared Function CallNextHookEx _
     (ByVal idHook As Integer, ByVal nCode As Integer, _
      ByVal wParam As IntPtr, ByVal lParam As IntPtr) As Integer
  End Function

  'Import for the UnhookWindowsHookEx function.
  <DllImport("User32.dll", CharSet:=CharSet.Auto, CallingConvention:=CallingConvention.StdCall)> _
     Public Overloads Shared Function UnhookWindowsHookEx _
       (ByVal idHook As Integer) As Boolean
  End Function

  'KeyboardHookStruct structure declaration.
  <StructLayout(LayoutKind.Sequential)> Public Structure KeyboardLLHookStruct
    Public vkCode As Integer
    Public scanCode As Integer
    Public flags As Integer
    Public time As Integer
    Public dwExtraInfo As Integer
  End Structure

#End Region

#Region "Constructor"

  Public Sub New()
    hookproc = AddressOf KeybordHookProc
    hHook = SetWindowsHookEx(WH_KEYBOARD_LL, hookproc, GetModuleHandle(Process.GetCurrentProcess().MainModule.ModuleName), 0)
    If hHook.Equals(0) Then
      MsgBox("SetWindowsHookEx Failed")
    End If
  End Sub

#End Region

#Region "KeybordHookProc"

  Private Function KeybordHookProc( _
    ByVal nCode As Integer, _
    ByVal wParam As IntPtr, _
    ByVal lParam As IntPtr) As Integer

    If (nCode < 0) Then
      Return CallNextHookEx(hHook, nCode, wParam, lParam)
    End If

    Dim hookStruct As New KeyboardLLHookStruct()
    hookStruct = CType(Marshal.PtrToStructure(lParam, hookStruct.GetType()), KeyboardLLHookStruct)

    Dim e As New System.Windows.Forms.KeyEventArgs(DirectCast(hookStruct.vkCode, System.Windows.Forms.Keys))
    OnKeyboardEvents(e)

    'キーCancelなら継続しない
    If (e.Handled = True) Then
      Return 1
    End If
    Return CallNextHookEx(hHook, nCode, wParam, lParam)
  End Function

#End Region

#Region "OnKeyboardEvents"

  Protected Sub OnKeyboardEvents(ByVal e As KeyEventArgs)

    RaiseEvent KeyboardEvents(Me, e)

  End Sub

#End Region

  Public Sub Dispose() Implements System.IDisposable.Dispose

    If (hHook > 0) Then
      UnhookWindowsHookEx(hHook)
    End If

  End Sub


End Class



潰す側(コントロールをラップ)


・ライブラリ初期化と解放
・イベントでF3が来るのを監視しておき、F3が来て、かつ対象のコントロールの場合、イベントキャンセル


  'F3潰し用のHookイベントハンドラ
  Private keyHook As KeyboardHook

  Protected Overrides Sub OnCreate()
    MyBase.OnCreate()

    If (Me.DesignMode = False) Then
      keyHook = New KeyboardHook()
      AddHandler keyHook.KeyboardEvents, AddressOf keyHook_KeyboardEvents
    End If

  End Sub
  Private Sub keyHook_KeyboardEvents(ByVal sender As Object, ByVal e As KeyEventArgs)

    'F3は潰す
    If (e.KeyCode = Keys.F3) Then
      If TypeOf (DirectCast(Me.TopLevelControl, System.Windows.Forms.Form).ActiveControl) Is エラーを起こすコントロールの型 Then
        e.Handled = True
      End If
    End If
  End Sub

  Protected Overrides Sub OnDestroy()
    If (Me.DesignMode = False) Then
      If Not (keyHook Is Nothing) Then
        keyHook.Dispose()
      End If
    End If
    MyBase.OnDestroy()
  End Sub

2014年2月4日火曜日

OracleClient(ODP.net)とBindingRedirect

Oracle Client 10.2.0.1で稼働していたシステムを、Windows7対応により、10.2.0.5へバージョンアップをします。

まず、OracleClient10.2.0.1がインストールされている環境で作成したモジュールを、
10.2.0.5環境で動かすと、例外エラーが出ます。

【エラー内容】
ファイルまたはアセンブリ 'Oracle.DataAccess, Version=10.2.0.100, Culture=neutral, PublicKeyToken=89b483f429c47342'、またはその依存関係の 1 つが読み込めませんでした。指定されたファイルが見つかりません。

これは、side-by-side実行 という.netの標準動作であり、
ビルドした時に使用したモジュールのバージョンを実行時のも保持している事が理由で
このエラーは、ビルド時のモジュールがないからと発生するものです。

詳しくは、@ITあたりで。
http://www.atmarkit.co.jp/fdotnet/technology/idnfw11_04/idnfw11_04_01.html

対処法の1つとして、bindingRedirectという仕組みがあります。
簡単に言うと、バージョンをリダイレクトし、異なるバージョンへ飛ばすものです。

これで、該当モジュールが存在しないときに、別のバージョンを参照することができます。
設定は、app.configに記載する必要があります。

【記載例】
    <runtime>
        <assemblyBinding xmlns="urn:schemas-microsoft-com:asm.v1">
            <dependentAssembly>
                <assemblyIdentity name="Oracle.DataAccess" publicKeyToken="89B483F429C47342"/>
                <bindingRedirect oldVersion="10.2.0.000-10.2.0.999" newVersion="1.102.2.20"/>
            </dependentAssembly>
        </assemblyBinding>
    </runtime>


ここで、「ん?」と思ったかもしれませんが、
ODP.netのバージョン番号の付与方法は、ODP10.2.0.3以降より、大幅に変わっています。

簡単に言うと、10.2.0.2までは、ODP.netのバージョンとほぼ同等。
それ以降は、先頭にFrameworkのバージョン番号が付くようになります。

アセンブリはバージョンアップしているにもかかわらず、バージョン番号は下がっているようにみえる。
一瞬混乱しますが、bindingRedirectの仕組みは、バージョンダウンにも対応可能。
よって、本方法で動作します。

それじゃなければ、汎用的なbindingRedirectの記述方法で簡単に参照できるそうです。(未検証)


【追記】
別アプローチとして「発行者ポリシー」を作成する等方法があります。
これは、GACに対してBindingRedirectを設定されるようなイメージですが、
アプリを改修せずに実施できるので、選択肢として検討するのもいいかもしれません。


2014年2月3日月曜日

zabbixのログインパスワードを忘れてしまった場合の対処(管理者向け)

この手の記事はよく書いている気がします。

zabbixのWeb画面からログインするためのパスワードを忘れてしまった時の処置です。

以下のようにデータベースを直接修正すれば可能です。 

※ZABBIXのデータベース名がzabbixだった場合


# mysql -uroot -p zabbix

mysql> update users set passwd = 'd41d8cd98f00b204e9800998ecf8427e' where alias = 'Admin'; 

これでAdminユーザのパスワードが空白に設定されます。