メインコンテンツまでスキップ

データベースからの読み取り

データベース内のテーブルからデータを取得することは、一般的に "選択" や "フェッチ" と呼ばれていますが、Eggplant Functional とデータベースを使用する場合は "読み取り" データと呼ばれます。この返されたデータは、Eggplant Functional を用いたデータ駆動型テストなどのテストに情報を提供するために使用することができます。

テーブル内容の読み取り

データベーステーブルの内容をフェッチすることは、そのすべてのレコードを要求するだけの単純な作業となることがあります。

ノート

データベースを変更する必要がなく、ただ読み取りたいだけの場合は、writable データベース接続リストプロパティNo に設定してください。

例:

以下のコードは、Members 変数をレコードのリストに設定します。それぞれの行に対して一つのレコードがリスト内に格納されます。リスト内の各アイテムは Record オブジェクトで、テーブル内のその行の値を含むプロパティリストであり、テーブル内の各列に対してプロパティキーが存在します。Recordsについての詳細は、Records vs. Property Listsを参照してください。

put the records of memberTable into Members
ノート

単一のレコードだけが期待されるか、必要な場合、recordrecords の代わりに使用することができます。これにより、レコードのリストではなく、単一のレコードオブジェクトが返されます。

Important

この例のように、大きなテーブルの全てのレコードを変数に読み込むことは推奨されません。whereを使用するか、データベースのレコードをイテレーションする方法を参照してレコードをイテレーションしてください。

例:

この例では、Get コマンドを使用して、lastName列が "Smith" と等しいレコードのデータのみを取得します。whereは、レコードを選択するためのさまざまな基準を含めることができます。

get the records of memberTable where lastName is "Smith"

名前が "S" で始まるが、 "Smith" を除くすべてのレコードを取得するには、次のようにリクエストします:

get records of memberTable where lastName begins with "S" and lastName isn't "Smith"

例:

Get コマンドはまた、それ(参照:すべてについて "It")と一緒に使用することもできます:

set myDB to {type:"odbc", DSN:"MyDB"} -- データベース接続を定義
put table "film" of myDB into myTable -- 変数 myTable に特定のテーブルへの参照データを格納
get rental_rate of the record of myTable where title is "TERMINATOR" -- Get コマンドを使用して特定の映画のレンタル料を取得
if it is "$9.99" then log "Rental rate is correct!" -- ローカル変数 It を使用してレンタル料が正しいことを確認

Where式

データベーステーブルには、大量のレコード(数千、数十万、それ以上)が含まれている場合があります。このような大きさのテーブル全体をEggplant Functionalの変数に取り込むと、ローカルメモリの使用に影響を及ぼす可能性があります。このため、必要なレコードだけを要求できると便利なことがよくあります。where節はこれを実現し、必要なレコードだけをデータベースに要求することで、ネットワークトラフィックとローカルメモリ使用量の両方を最小限に抑えます。

Where式は、recordまたはrecords関数、number of records関数、またはdelete recordコマンドを使用して、テーブルから必要なレコードを選択するために使用されます。where節が指定されていない場合、テーブルのすべてのレコードが返されます。

ノート

このページで説明されているwhere節は、Each Expressionsで使用されるwhere節と混同しないでください。それらは似たようなことをしますが、非常に異なります。データベースで使用されるwhere式は能力が限られていますが、データベースからデータを取得する際にははるかに効率的になることができます。

where式はwhere節に続く式で構成されます。その式には、_columnName operator value_の形式を使用してテーブルを1つ以上参照するものが含まれます。列の名前は最初に来て、その後にオペレータ、そして値が続きます。たとえば、式 "where size is at least 12"では、列名は "size"、オペレータは "is at least"、値は "12"です。

例:

set mymovie to the record of films where title is "TERMINATOR"
ノート

where節で指定した条件に一致するレコードが複数ある場合、recordという語を使用すると、その中の最初のレコードのみが返されます。一致するすべてのレコードを返すにはrecordsを使用します。

オペレーター

where式を使用する場合、オペレーターは次のいずれか(またはそれらの同義語や否定形)にすることができます:

  • is equal to
  • is not equal to
  • is less than
  • is more than
  • is less than or equal to
  • is greater than or equal to
  • begins with
  • ends with
  • contains substring
  • is in list of values
  • is between min and max

これらのオペレータは、列に値が割り当てられているかどうかをテストするために使用できます:

  • columnName is null
  • columnName is not null

And/Or

さらに、ANDまたはORで条件を結合することで、複数の条件を一度にテストすることができます。複雑なwhere式では、括弧でサブ式を囲むと意味が明確になります。

例:

delete records from billingTable where (dueDate is earlier than today) and (remainingAmountDue is 0)

例:

//Displays the full name of the club member whose member number is 12345
put 12345 into desiredMemNum
set clubDBto (type:"odbc", DSN:"ClubData", user:"root", password:"")
put table "Members" of clubDB into memberTable
set member to the record of memberTable where memberNumber is desiredMemNum
put "Name: " & member's firstName && member's lastName

データベーステーブルのレコードを繰り返し処理する

データベーステーブルのレコードを繰り返し処理することは、レコードを更新したりデータを操作したりする一般的な方法です。これは、Repeat LoopまたはRecord Iteratorを使用して行うことができます。

Repeat Loopを使用する

SenseTalkのrepeat loopを使用してデータを繰り返し処理するためには、そのデータをデータベースから読み込んでスクリプトに取り込む必要があります。その後、他のSenseTalkスクリプトと同様に、取得したデータを繰り返し処理するためのrepeat loopを使用できます。

ノート

レコードを繰り返し処理し、反復処理中に修正を加える必要があるシナリオでは、Repeat with Each... By Referenceを使用します。これはReferences to Containersで説明されています。

例:

以下の例では、repeat loopを使用してデータベースから取得したユーザレコードを繰り返し処理し、各ユーザーのためのオンラインフォームを記入します:

set myDB to {type:"odbc", DSN:"mySQLDB", user:"root", password:"password123"} -- データベース接続情報を定義する
put the number of records in table "userInfo" in myDB into numRecords -- テーブル内のレコード総数を読み取り、その情報を変数numRecordsに格納する
Log "We will be entering" && numRecords && "records into the system." -- 何レコード利用可能かを宣言するメッセージをログに記録する
put table "userInfo" of myDB into users -- データベーステーブル"userInfo"へのアクセス情報を変数"users"に格納する
put the records of users into credentials -- "userInfo"テーブルからレコードを取得し、それらを変数credentialsに格納する
Log "Entering the following new users: " & credentials -- レコード自体を含むメッセージをログに記録する
repeat with each item user of credentials -- credentialsの各レコードに基づいて繰り返す
WaitFor 10, "Form_SubmitButton"
Click "Form_UsernameField"
typetext user.username -- 現在のレコードのusernameプロパティの値を参照し、その値をSUTに入力する
Click "Form_PasswordField"
typetext user.password
Click "Form_SubmitButton"
Click "Form_AddNewUser"
end repeat

例:

プロパティリストは、キーを使用して値を特定するリストです(詳細はプロパティリストを参照)。この例では、プロパティキーがどのようにしてデータの異なる部分を特定し、操作するために使用できるかを示しています。これは単独の例で、実際にはデータベースに接続する必要はありませんので、ご自身のシステムで実行してみてください。

// カラム名でアイテムキーを使用する
set dbResults to { {name:"Roger", age:17}, {name:"Arabella", age:32}, {name:"Francis", age:29}, {name:"Balthazar", age:92},
}
put the keys of item 1 of dbResults into columnNames
put columnNames
put columnNames joined by comma into header
put header & return into csvContents

repeat with each record of dbResults
repeat with each key in columnNames
if the counter > 1 then put comma after csvContents
put record.(key) after csvContents
end repeat
put return after csvContents
end repeat
put csvContents

以下は、前述の例の短縮版であり、データベースに接続せずに実行するために書かれたものであり、デモンストレーション目的のため、ご自身のマシンで実行してみてください。

// カラム名でアイテムキーを使用する
set dbResults to{ {name:"Roger", age:17}, {name:"Arabella", age:32}, {name:"Francis", age:29}, {name:"Balthazar", age:92},
}
put the keys of item 1 of dbResults joined by comma & return into csvContents
repeat with each record of dbResults
put values(record) joined by comma & return after csvContents
end repeat
put csvContents

レコードイテレータの使用

テーブルから一連のレコードをリストとして取得する代わりに、一度に1つのレコードを反復処理する_レコードイテレータ_を取得することができます。イテレータをリストとして扱う(as a list 演算子を使用する場合など)と、残りのすべてのレコードがフェッチされます。レコードイテレータは、一部の状況で便利であるかもしれませんが、全てのデータが一度にデータベースからフェッチされ、要求された時にのみレコードオブジェクトに変換されるため、repeatループと比べて非常に小さいパフォーマンス上の利点しか提供しません。SenseTalkのイテレータについての詳細は、Iteratorsを参照してください。

SenseTalkでレコードイテレータにアクセスする方法は2つあります。

useRecordIteratorプロパティの設定

可能な場合にはレコードイテレータを返すようにuseRecordIteratorプロパティをtrueに設定します。

set the useRecordIterator of myTable to Yes

直接イテレータを要求する

直接イテレータを要求するためには、データベースリクエスト内で"iterate over the records of"を使用します。

set memberIterator to iterate over the records of memberTable

次のレコードは、イテレータのnextValueプロパティを使用して取得することができます。

put memberIterator's nextValue into currentMember

データベーステーブルのレコード数をカウントする

データベーステーブルのレコード数をカウントするには、Number of Records関数を使用します。

Number of Records関数

振る舞い: 指定されたテーブルのレコード数を返します。RecordsまたはRowsのどちらでも交換可能に使用できます。

パラメータ: テーブル。テーブルを参照するtable表現または変数とペアにする必要があります。

文法:
[構文:> {the} number of [rows | records] [of | in] table {where whereExpr}

ノート

上記の構文中の_Table_は、テーブルを参照に設定した変数、またはtable表現(table tablename of database)のどちらかです。

例:

テーブルの_レコード数_を直接尋ねると、データベースに_count_リクエストが送信されます。カウントリクエストは、レコードではなく数値を返します。これは、レコードをフェッチして返されたリストのアイテム数を尋ねるよりも効率的です。これは、大量のレコードを含むテーブルを操作するときに安全な方法です。この例では、データベーステーブルに何レコードがあるかを調べるためにnumber of recordsを使用しています。

put the number of records of table "colorpalette" of myDB

例:

データベーステーブルで特定の条件に一致するレコードがいくつあるかを調べる別の方法は、テーブル参照を変数に保存し、次にnumber of records関数を、オプションのwhere句(Where Expressions参照)と共にテーブル変数に適用することです。次の例を参照してください。

put table "colorpalette" of myDB into colors -- Stores a reference to the table in a variable.
get number of records of colors where color is "green" --
Log "There are " & it & " record(s) in the table."

Log "There are " & it & " record(s) in the table."

小さいテーブルを扱うのに適した別の方法です。この方法はよりシンプルですが、慎重に使用する必要があります。また、すべてのレコードをSenseTalkに持ち込みたいと知っている場合に使用します。

put the records of table "memberinfo" of myDB into members
put the number of items in members

例:行数の変化の数

レコード(行)数の行数のバリエーションを使用して、データベーステーブル内で特定の条件に一致するレコードが何件あるかを調べます:

put the number of rows of table "colorpalette" of myDB where "color" is "black"

例:

テスト実行の開始時に追加されるレコード数を宣言するために、number of records関数を使用します:

set myDB to (type:"odbc", DSN:"mySQLDB", user:"root", password:"password123")
put the number of records in table "users" in myDB into numRecords -- Stores the total number of records in the table into variable numRecords
Log "We will be entering" && numRecords && "records into the system." -- Logs a message to declare how many records are available