Linuxサーバー構築~その3~
<はじめに>
Linuxサーバー構築シリーズその3です。
※Linuxサーバー構築シリーズその2の訂正
・ghcはyumでインストールせずに、ghc7.6.3とhaslkell-platformを
ソースからインストールします。
・httpdをyumでインストールしました。
configの設定は次回以降で書きます。
<実施内容>
さて、今回はghcとhaskell-platformをインストールします。
haskell-platformにはghcが含まれるようなのですが…
とりあえず、先にインストールを試みます。
// ダウンロード sudo wget http://www.haskell.org/platform/download/2013.2.0.0/haskell-platform-2013.2.0.0.tar.gz // チェックサムの確認 sha1sum haskell-platform-2013.2.0.0.tar.gz // 展開 tar xvzf haskell-platform-2013.2.0.0.tar.gz
と、ここでREADMEの中を見てみると…
どうもghc7.6.3が必要みたいですね。
そこで、ghcのダウンロードサイトを確認すると
最新版(2013年12月11日時点)が7.6.3でしたので、これをインストールします。
// ダウンロード sudo wget http://www.haskell.org/ghc/dist/7.6.3/ghc-7.6.3-x86_64-unknown-linux.tar.bz2 // 展開 tar xvfj haskell-platform-2013.2.0.0.tar.gz // .configureの実行 ./configure --prefix=/usr/local/haskell/ghc/7.6.3 // インストール sudo make install
これで、ghcのインストールは無事に完了したはずです。
いざ、haskell-platformのインストール!…と、いきたいことろですが
このままだとgmplibが無えよ!って怒られます。
さらにzlibも無えよ!って怒られます。
ついでにOpenGLのライブラリが無えよ!とも怒られるみたいです。
それらのライブラリをインストールします。
// gmpのインストール sudo wget https://ftp.gnu.org/gnu/gmp/gmp-5.1.3.tar.bz2 tar xjvf gmp-5.1.3.tar.bz2 ./configure make make check sudo make install // /etc/ld.so.confの編集 >include ld.so.conf.d/*.conf > >/usr/lib >/usr/local/lib sudo ldconfig // zlibのインストール sudo wget http://zlib.net/zlib-1.2.8.tar.gz tar zxvf zlib-1.2.8.tar.gz ./configure make sudo make install // freeglut-develのインストール sudo yum -y install freeglut-devel
これでようやくhaskell-platformがインストールできます。
// haskell-platformのインストール ./configure --prefix=/usr/local/haskell/haskell-platform/2013.2.0.0 make sudo make install // cabalのupdateもしておきます cabal update
<まとめ>
今回でghcが使えるようになりました。
次回はiptablesやApacheのあたりを設定していく予定です。
Linuxサーバー構築~その2~
<はじめに>
Linuxサーバー構築シリーズその2です。
前回その1ではOSのインストールやNICの有効化を実施しました。
さらに起動プロセスの確認を行います。
/etc/yum.repo.d/CentOS-Base.repoの内容を編集します。
[base],[updates],[extras],[centosplus],[contlib]の値について
初期値はbaseurlがコメントアウトされているので、
編集内容を保存してyum updateを実施します。
yumのログは/var/log/yum.log に出力されるので中身も確認すると、
先ほどアップデートしたパッケージのログが確認できます。
□ssh公開鍵の作成
CentOS 6.4をインストールするとsshが最初からインストールされていて
OS起動時にsshdも起動しています。
また、iptablesを確認すると22番ポートも開いています。
このままでもユーザーとパスワードでならばログインすることも可能ですが、
今回のサーバーはアクセスするクライアントが固定なので公開鍵を使用します。
作成した公開鍵を下記のファイル名で保存します。
~/.ssh/authorized_keys
この時.sshフォルダの属性を700に、
authorized_keysファイルの属性を600に変更しておきます。
公開鍵を利用してアクセスできることが確認できたら
パスワードによるアクセスを制限します。
/etc/ssh/sshd_configファイルのパスワード認証をnoに変更し、
その後、sshdを再起動します。
□起動プロセスの確認
起動プロセスはps axで確認します。
また、LISTEN状態のポートをnetstatで、
さらに外部からのポートの状態をnmapで確認します。
※どのプロセスがどのポートを使用しているかについては
lsofコマンドで詳細が見えるようです。
netstatで確認すると、22番ポートと25番ポートがLISTEN状態でした。
心当たりがないのでyumでインストールしたlsofコマンドで確認してみると
やはり、smtpでLISTENされているみたいです。
そこで、runlevelとchkconfigを確認してみると、
いました!postfixがrunlevel3でonになっているようです。
不要なので下記のコマンドで切っておきます。
chkconfig --level 23 postfix off
最後にnmapで確認すると、22番ポートだけが空いています。
□必要なパッケージのインストール
本題からは外れますが、下記のパッケージをインストールしておきます。
バージョンは特にこだわらないのでパッケージの管理はyumに任せます。
・nslookup
・traceroute
・gcc
・make
・cpp
・ghc(12/11削除)
・perl
・httpd(12/11追加)
・rpcbind(14/08/16追加)
・vim(14/08/16追加)
・lsof(14/08/16追加)
・ntp(14/08/16追加)
※nslookupはbind-utilsパッケージに含まれます。
<まとめ>
今回までの作業で、sshでつなげて、yumが使えるようになりました。
また、余分なプロセスを切ることができました。
次回はWebサーバーをインストールしてCGIを作成してみることにします。
Linuxサーバー構築~その1~
<はじめに>
Linuxでサーバー構築を行う様を記録していきます。
下記の4つの役割を実装することを目標にすすめます。
・ドメインコントローラー
・ファイルサーバー
・DNSサーバー
・バージョン管理サーバー
<作業内容>
まずはOSのインストールを行います。
今回構築するのはCentOS6.4です。
最終的にはHP ProLiant MicroServerに構築しますが、
今回は検証も兼ねてWindows7上のVirtualBoxにインストールします。
インストールの時に注意するのは2点です。
□ネットワークの詳細
上の画像の「自動接続する」のチェックはデフォルトで入っていません。
このチェックが入っていないとOS起動後に手動でNICを有効にしないといけません。
□パーティションの分割
今回は上の画像のように分割しました。
ファイルサーバーの割に /home が少ないのは
ホストOSのHDDの空き容量がわずかな故です。 ^^;
実際このあたりは自由に分割しちゃっていいと思います。
注意点として、基本パーティションは最大4つまでしか分割できません。
/ や 特に /boot なんかは基本パーティションに割り当てないといけません。
/home や /var なんかは拡張パーティションに割り当ててもおkです。
引き続きMinimalでインストールを続けて、
必要なものは随時インストールすることにします。
OSのインストールが無事に済んだら作業用のユーザーを作ります。
コマンドは下記。
# adduser <ユーザー名>
# passwd <ユーザー名>
本来ならこの時点でグループも決めた方がいいかもしれません。
今のところユーザーはroot、作業用、ファイルサーバー用の3つなので、
グループはスルーして進めます。
次に作業用のユーザーにsudo権限を付与します。
# visudo
//------------------------------------------------------
/etc/sudoers
# Arrows root to run any commands anywhere
<ユーザー名> ALL=(ALL) ALL // 追加
//------------------------------------------------------
これで、先ほど作ったユーザーで sudo コマンドが利用できるようになります。
さて、インストールの際にネットワークの自動接続に
チェックをしなかった場合はNICを有効にしないといけません。
まずは設定ファイルを編集します。
//------------------------------------------------------
/etc/sysconfig/network-scripts/ifcfg-eth0
DEVICE=eth0
HWADDR=FF:FF:FF:FF:FF:FF
TYPE=Ethernet
UUID=xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx
ONBOOT=yes // ここをyesにすることで、起動時にNICが有効になるようです。
NM_CONTROLLED=yes
BOOTPROTO=static
IPADDR=xxx.xxx.xxx.xxx // IPアドレスを指定します。
NETMASK=xxx.xxx.xxx.xxx // サブネットマスクを指定します。
GATEWAY=xxx.xxx.xxx.xxx // ゲートウェイを指定します。
//------------------------------------------------------
次にNICを有効にします。
#ifdown eth0 // eth0の無効化
#ifup eth0 // eth0の有効化
ついでにDNSサーバーも指定します。
//------------------------------------------------------
/etc/resolv.conf
nameserver xxx.xxx.xxx.xxx
//------------------------------------------------------
一通り設定し終わったら確認です。
ネットワークの設定は下記のコマンドで確認します。
#ifconfig // ネットワークの情報
#nslookup // DNSサーバーの情報
#traceroute // ルーティングの情報
#tracepath // ルーティングの情報
この時点ではnslookupとtracerouteはインストールされていないので、
後ほどパッケージをインストールしたときに確認します。
<まとめ>
この回ではOSのインストールとユーザーの作成、ネットワークの設定を実施しました。
次回はyumのリポジトリと浮いてるプロセスなんかを確認します。
また、次回以降必要なパッケージやサーバーをインストールしていきます。
F# で Oracle にアクセスしてみたよ!
<はじめに>
この記事は F# Advent Calendar 2013 7日目の記事です。
6日目は@masaru_b_clさんの F# InteractiveをConEmu上で利用する でした。
さて、F#を勉強し始めて、プライベートでちょいちょい書いていると、
「そのうち業務でもF#使いたいなー?」なんて妄想したりしますよね?
いざF#を業務に導入するとなると、
きっと既存の情報資産を活用できて、かつインパクトが少ない
例えば小規模なマスタメンテ用のWebサービスの作成ぐらいから
始めていくのが現実的かなー?なんて思ったりします。
今回はそんな来るべき日に備えて、
「ADO.NETを使ってF#でOracleにアクセスする方法」
を覚書程度に書いてみました。
<対象データ>
下記のテーブルからデータを取得します。
<プログラム1>
とりあえず、コンソールアプリケーションで単純にOracleからデータを取得してみます。
OracleClientはOracle.DataAccess.Clientを利用します。
open System open System.Data open System.Configuration open Oracle.DataAccess.Client [<EntryPoint>] let main(args : string[]) = // 接続文字列の取得 let conStr = ConfigurationManager.ConnectionStrings.Item "connection" let con = new OracleConnection(conStr.ToString()) // SQLの定義 let sqlStr = "SELECT * FROM MEMBER WHERE ID = 1" let cmd = new OracleCommand(sqlStr, con) con.Open() // データの取得 let reader = cmd.ExecuteReader() let result = reader.Read() // 取得したデータの出力 printfn "%s %s %s %s" (reader.GetString(0)) (reader.GetString(1)) (reader.GetString(2)) (reader.GetString(3)) reader.Close() con.Close() 0
ちなみに接続文字列はApp.configから取得しています。
中身はこんな感じです。
<?xml version="1.0" encoding="utf-8" ?> <configuration> <connectionStrings> <add name="connection" connectionString="Data Source=XE;User ID=hoge;Password=fuga;"></add> </connectionStrings> </configuration>
<実行結果1>
上手くデータが取得できました!
<プログラム2>
目標はマスタメンテ用のWebサービスを作ることなので、
次はWebサービスを作ってみることにします。
open System open System.IO open System.Data open System.Configuration open Oracle.DataAccess.Client open FSharpWcfServiceApplicationTemplate.Contracts type Service1() = interface IService1 with member x.GetOracle value = // 接続文字列の取得 let conStr = ConfigurationManager.ConnectionStrings.Item "string1" let con = new OracleConnection(conStr.ToString()) // SQLの定義 let sqlStr = "SELECT * FROM MEMBER WHERE ID = " + value let cmd = new OracleCommand(sqlStr, con) con.Open() // データの取得 let reader = cmd.ExecuteReader() try try let a = reader.Read() sprintf "%s %s %s %s" (reader.GetString(0)) (reader.GetString(1)) (reader.GetString(2)) (reader.GetString(3)) with | :? FormatException as e -> e.Message | :? IOException as e -> e.ToString() | _ as e-> "???" finally reader.Close() con.Close()
<実行結果2>
デバッグで引数に"2"を渡して実行してみた結果がこちら。
こちらも上手く値が返ってきました。
<プログラム3>
それでは最後に、C#で書かれた適当なクライアントから
先ほど作ったWebサービスをサービス参照で呼び出してみます。
public Form1() { InitializeComponent(); } private void button1_Click(object sender, EventArgs e) { var webService = new FSservice.Service1Client(); this.textBox1.Text = webService.GetOracle("3"); }
<実行結果3>
おー!値が取得できました!
<まとめ>
F#を使って(というかADO.NETを使って)Oracleにアクセスすることができました。
取得したデータをF#でいかに扱うかを勉強していきたいと思います。
F# AdventCalender 2013 7日目は以上です。
明日は@n_enotさんの「F# で System.Reflection(仮)」です。
Hello Haskell!
<はじめに>
なんてことはない、単にHaskellを書いてみたかったというプログラム。
<プログラム>
main = putStrLn "Hello Haskell!"
<まとめ>
これから勉強していきます。
PhotoCameraを使ってみる
<はじめに>
スマホアプリにカメラは外せないので調べてみました。写真を撮ってカメラロールに保存するだけの簡単なプログラムを書いてみました。
<プログラム>
public partial class MainPage : PhoneApplicationPage { //----------------------------------- // インスタンス変数 // int photoCounter = 0; PhotoCamera photoCamera; MediaLibrary mediaLibrary; //----------------------------------- // コンストラクタ // public MainPage() { InitializeComponent(); InitializePhotoCamera(); InitializeMediaLibrary(); } //----------------------------------- // photoCamera初期化 // public void InitializePhotoCamera() { photoCamera = new PhotoCamera(Microsoft.Devices.CameraType.FrontFacing); viewfinderBrush.SetSource(photoCamera); photoCamera.CaptureImageAvailable += new EventHandler<ContentReadyEventArgs>(photoCamera_CaptureImageAvailable); } //----------------------------------- // mediaLibrary初期化 // private void InitializeMediaLibrary() { mediaLibrary = new MediaLibrary(); } //----------------------------------- // キャンバスをタップ // private void canvas1_Tap(object sender, GestureEventArgs e) { try { photoCamera.CaptureImage(); } catch (Exception ex) { MessageBox.Show(ex.Message); } } //----------------------------------- // イメージの取得 // void photoCamera_CaptureImageAvailable(object sender, ContentReadyEventArgs e) { try { photoCounter++; string fileName = photoCounter + ".jpg"; mediaLibrary.SavePictureToCameraRoll(fileName, e.ImageStream); } catch (Exception ex) { Dispatcher.BeginInvoke(() => MessageBox.Show(ex.Message)); } } }
<まとめ>
やってることはphotoCameraのインスタンスを生成して、CaptureImageAvailableイベントに画像を保存するメソッドを定義して、photoCameraのCaptureImageメソッドを呼び出しているだけです。ただし、これだけだとカメラで取得した画像の上下がわけわかんなくなってしまうので、WP自体の回転に応じて画面も回転させてやらないといけません。
Compass、Motion、ときどきGyroscope
<はじめに>
WP7で使えるセンサーについて調べてみました。フレームワークで使えそうなクラスにGyroscope、Compass、Motionがあったので、それぞれを使って実装を試してみました。
<プログラム>
public partial class MainPage : PhoneApplicationPage { //-------------------------------------------- // インスタンス変数 // Gyroscope gyroscope; Compass compass; Motion motion; //-------------------------------------------- // コンストラクタ // public MainPage() { InitializeComponent(); GyroscopeInitialize(); CompassInitialize(); MotionInitialize(); } #region センサー初期化メソッド //-------------------------------------------- // ジャイロスコープ // public void GyroscopeInitialize() { gyroscope = new Gyroscope(); gyroscope.CurrentValueChanged += new EventHandler<SensorReadingEventArgs<GyroscopeReading>>(gyroscope_CurrentValueChanged); //gyroscope.Start(); } //-------------------------------------------- // コンパス // public void CompassInitialize() { compass = new Compass(); compass.CurrentValueChanged += new EventHandler<SensorReadingEventArgs<CompassReading>>(compass_CurrentValueChanged); compass.Start(); } //-------------------------------------------- // モーション // public void MotionInitialize() { motion = new Motion(); motion.CurrentValueChanged += new EventHandler<SensorReadingEventArgs<MotionReading>>(motion_CurrentValueChanged); motion.Start(); } #endregion #region イベント用メソッド //-------------------------------------------- // ジャイロスコープ // void gyroscope_CurrentValueChanged(object sender, SensorReadingEventArgs<GyroscopeReading> e) { GyroscopeReading gyroscopeReading = e.SensorReading; Vector3 rotationRate = gyroscopeReading.RotationRate; Dispatcher.BeginInvoke(() => this.textBlockRotationX_value.Text = rotationRate.X.ToString()); Dispatcher.BeginInvoke(() => this.textBlockRotationY_value.Text = rotationRate.Y.ToString()); Dispatcher.BeginInvoke(() => this.textBlockRotationZ_value.Text = rotationRate.Z.ToString()); } //-------------------------------------------- // コンパス // void compass_CurrentValueChanged(object sender, SensorReadingEventArgs<CompassReading> e) { CompassReading compassReading = e.SensorReading; double headingAccuracy = compassReading.HeadingAccuracy; double magneticHeading = compassReading.MagneticHeading; Vector3 magnetometerRating = compassReading.MagnetometerReading; double trueHeading = compassReading.TrueHeading; Dispatcher.BeginInvoke(() => this.textBlockheadingAccuracy_value.Text = headingAccuracy.ToString()); Dispatcher.BeginInvoke(() => this.textBlockMagnetic_value.Text = magneticHeading.ToString()); Dispatcher.BeginInvoke(() => this.textBlockMagnetX_value.Text = magnetometerRating.X.ToString()); Dispatcher.BeginInvoke(() => this.textBlockMagnetY_value.Text = magnetometerRating.Y.ToString()); Dispatcher.BeginInvoke(() => this.textBlockMagnetZ_value.Text = magnetometerRating.Z.ToString()); Dispatcher.BeginInvoke(() => this.textBlockTrueHeading_value.Text = trueHeading.ToString()); } //-------------------------------------------- // モーション // void motion_CurrentValueChanged(object sender, SensorReadingEventArgs<MotionReading> e) { MotionReading motionReading = e.SensorReading; AttitudeReading attitude = motionReading.Attitude; Vector3 deviceAcceleration = motionReading.DeviceAcceleration; Vector3 deviceRotatingRate = motionReading.DeviceRotationRate; Vector3 Gravity = motionReading.Gravity; Dispatcher.BeginInvoke(() => this.textBlockPitch_value .Text = attitude.Pitch.ToString()); Dispatcher.BeginInvoke(() => this.textBlockYaw_value.Text = attitude.Yaw.ToString()); Dispatcher.BeginInvoke(() => this.textBlockRoll_value.Text = attitude.Roll.ToString()); } #endregion }
<まとめ>
端末に機能がないのかGyroscopeは上手く使えなかったのですが、CompassとMotionからは値の取得ができました。センサー関連のクラスは使い方がほぼ同じなのでいろいろ活用できそうです。