カテゴリ:SQL( 30 )
(SQL)テーブル名にハイフン入ってる時はクォートする必要あり
SQLiteでついハイフン(-)入のテーブルを作ってしまい、以下の用なクエリを実行したらエラーになりました。
SELECT * FROM hoge-test WHERE name='moe';

テーブル名にハイフンが入っていると、ダメなようです。
これは、SQLiteに限らず他のDBMS(MySQLやSQL Server)も同様みたいです。

解決策としては、ハイフンを付けないか、以下のようにクォートしてやるかです。
SELECT * FROM 'hoge-test' WHERE name='moe';


しばらくSQLやDB触ってないとこうなっちゃいますね。

参考:
PHP+SQLの覚え書き: テーブル名にハイフンはご法度
龍の記憶:SQLServer SQL のテーブル名に - (半角ハイフン) - livedoor Blog(ブログ)
[PR]
by Jehoshaphat | 2012-11-30 23:22 | SQL | Trackback | Comments(0)
SQLiteManagerでUTF-8でデータを保存したい
SQLite内のデータベースを容易に管理するためにPHP上で動く SQLiteManager を入れてみたんですが、どうやら日本語に設定するとEUC-JPで動くらしく、UTF-8のデータをみると文字化けします。


ということで SQLiteManager でUTF-8のデータを扱う方法ですが、languageファイルの文字コードと定義を変更すればいいようです。

まず下記ファイルをテキストエディタで開きます。
lang\japanese.inc.php

文字コード定義部分を下記のように修正します。

/*
$charset = 'euc-jp';
$langSuffix = 'ja-euc';
↓*/

$charset = 'utf-8';
$langSuffix = 'ja-utf-8';

後は、languageファイルをUTF-8で保存します。
これでUTF-8を扱えるようになりました。

参考:
MAMP に入っている SQLiteManager の文字コードを UTF-8 に変更する - 転校生@Hatena
[PR]
by jehoshaphat | 2011-07-01 01:56 | SQL | Trackback(3) | Comments(0)
(MySQL)ログイン時のパスワード指定と外部SQLファイルの実行
余り普段使わない MySQL ではログインでも四苦八苦する時があります。

(MySQL)スクリプトファイルからクエリを実行する方法では、MySQLクライアントにログインしてから外部ファイルを読み込んでますが、今回はコマンドラインから直接外部ファイルを読み込むための方法です。

こんな感じでOKみたいです。

>mysql -h ホスト名 -u ユーザ -pパスワード DB名 < hogehoge.sql


ハマったのは -p の後に空白入れずにパスワードを入れる部分ですね。(空白を入れてしまっていました)
外部ファイルは入力リダイレクト(<)でファイルを指定するだけでいけます。
[PR]
by jehoshaphat | 2009-08-21 10:57 | SQL | Trackback | Comments(0)
(SQL)SQL Server 2005 でDBログインユーザとデータベースユーザの一覧取得
SQL Server のデータベースログインユーザと、各データベースのユーザをSQLで列挙する方法です。

ログインユーザは master データベースの syslogins テーブルに定義されているようです。
データベースユーザは各データベースの sysusers テーブル定義されているようです。

下記のようなSQLで確認できます。

/*ログインユーザ列挙*/
USE master;
SELECT * FROM syslogins;
 
/*データベースユーザ列挙*/
USE DB名;
SELECT * FROM sysusers;
 
/*おまけ。データベースの一覧列挙*/
USE master;
SELECT name FROM sysdatabases;


参考:
KYO'S ROOM 【SQL Server】:
[PR]
by jehoshaphat | 2009-08-10 18:36 | SQL | Trackback | Comments(0)
OLEDB JETでクエリを投げると、式が複雑すぎますと怒られた

ADO.Net を使って MDBへ のクエリ実行時に「式が複雑すぎます。」という例外で怒られました。

確かに、WHERE句に相当数の条件を入れています。
例えばこんな感じ。(パラメータクエリを使ってます。詳しくは(ADO.Net)OLEDB経由でのMDBへの副問い合わせにパラメータクエリを使うとおかしくなることがある)

PARAMETERS
pCondBirthday1 Char ,
pCondBirthday2 Char ,
pCondBirthday3 Char ,
pCondPref1 Text ,
pCondPref2 Text ,
pCondPref3 Text ;
SELECT *
FROM Customer
WHERE
(
Birthday = pCondBirthday1 OR
Birthday = pCondBirthday2 OR
Birthday = pCondBirthday3 OR
[省略]
) AND (
Pref = pCondPref1 OR
Pref = pCondPref2 OR
Pref = pCondPref3 OR
[省略]
)

どうやら WHERE句に条件大量にあるとダメみたいです。具体的のどれくらいの数を超えたらNGかというのは見つかりませんでした。

で、上記のSQLの場合、特に一つのフィールドに対して複数の OR 条件が大量の設定してます。
これは IN句を使うべきと同僚に言われてました。
言われてみれば、そんなのもあったなと。。今まで、副問い合わせで複数値が返るときにか使ってませんでした。。

ということで、下記のように OR 条件を IN句に置き換えたらエラーはでなくなりましたとさ。
(パラメータ定義部分は省略)

SELECT *
FROM Customer
WHERE
Birthday IN ( pCondBirthday1 ,
pCondBirthday2 ,
pCondBirthday3 ,
[省略]
)
AND
Pref IN ( pCondPref1 ,
pCondPref2 ,
pCondPref3 ,
[省略]
)

ま、結局は3流PGのSQLの知識不足ということでした。

参考:
「式が複雑すぎます」の具体的な条件
[PR]
by jehoshaphat | 2009-08-02 01:13 | SQL | Trackback | Comments(0)
AccessとOLEDB JET経由でLIKE文のワイルドカードが変わる

Access で LIKE 演算子で0文字以上の文字を表す時は * を使いますよね。
ところが、JETエンジン使って mdb にアクセスする OLEDB経由の ADO.Net だと % という純粋なSQLに近い形しないとダメなようです。

/*Accessだとヒットする。 OLEDB経由だとヒットしない*/
SELECT *
FROM Customer
WHERE Address LIKE '*京都*'
 
/*Accessだとヒットしない。 OLEDB経由だとヒットする*/
SELECT *
FROM Customer
WHERE Address LIKE '%京都%'


Access でテスト用のクエリを書いて、.Net のコードに移植してたんですが、これに気付かずちょっとハマってしまいした。
Visual Studio 上のサーバエクスプローラから mdf ファイルを指定し、クエリたたけば OLEDB 経由になるので、これからはこっち使ったほうが安全ですね。

この仕様については、Microsoft Jet SQL と ANSI SQL との比較で解説されてます。
下記の引用部分が、その仕様について言ってるところですね。
ANSI SQL のワイルドカード文字を使用できるのは、Jet 4.x と Microsoft OLE DB Provider for Jet を組み合わせて使う場合だけです。Microsoft Access または DAO を介して ANSI SQL のワイルドカード文字を使うと、リテラルとして解釈されます。Microsoft OLE DB Provider for Jet と Jet 4.x を使用しているときは、Jet SQL のワイルドカード文字がリテラルとして解釈されます。
[PR]
by jehoshaphat | 2009-07-31 12:39 | SQL | Trackback | Comments(0)
(SQL)現在の日時を数値(整数)で落としたい

SQL Server で現在日時を取得して、整数の文字列として保存する方法です。
あんまり需要は無いかもしれませんが、今回保存する汎用テーブル構造が キー:nvarchar(50) , 値:nvarchar(50) なので、こういう方法で。。。

下記のように convert 関数を使って、いったん timestamp 型に変えた後、bigint に変える方法にしてみました。
bigint の値から nvarchar 型のフィールドへは暗黙的キャストで入れれるので、特に何もしてません。

convert(bigint, convert(timestamp,GETDATE(),121 ),2)


参考:
TechNet:CAST および CONVERT (Transact-SQL)
TechNet:データ型 (Transact-SQL)
[PR]
by jehoshaphat | 2009-07-18 00:19 | SQL | Trackback | Comments(0)
(SQL Server)データベース復元時に必要な権限
あるデータベース専用のユーザを作って、db_owner のロールを与えてます。
バックアップもうまくいったんで、てっきり復元もできるかと思ったら、

System.Data.SqlClient.SqlError: ユーザーにはデータベース 'データベース名' を復元する権限がありません。
重要度:14
SQL Serverエラーナンバー:3110

と怒られました。

で調べてみると、復元を実行するユーザは以下のいずれかのメンバでないとけないようです。
・dbo
・sysadminサーバロール
・dbcreatorサーバロール

dbo というのは未だにちょっと概念が分かってないんで、とりあえず dbcreater サーバロールのメンバにユーザ加えることで対応しました。

参照:
MSDN:RESTORE (Transact-SQL)の権限の項目
[PR]
by jehoshaphat | 2009-07-17 23:49 | SQL | Trackback | Comments(0)
(SQL Server)データベースの復元時にエラーナンバー:3102が発生
ある SQL Server のユーザでログインし、データベースを復元しようとすると下記のようなエラーが。。。


System.Data.SqlClient.SqlError: データベース 'データベース名' はこのセッションで使用中なので、RESTORE では処理できません。この操作を実行するときは、master データベースを使用することをお勧めします。
重要度:16
SQL Serverエラーナンバー:3102


いろいろ探してると、CodeHour:SQL Server で復元できない時にピンポイントな答えが。。
どうやら、復元処理を実行しているユーザの「既定のデータベース」と復元先のデータベースが同じためにおこるらしいです。

ということ、SQL Server ユーザ作るときに、最初から既定のデータベースを master にすることにしました。
[PR]
by jehoshaphat | 2009-07-17 23:38 | SQL | Trackback | Comments(0)
(SQL Server)バッチでシステムドライブにあるmdfファイルをアッタチさせようとしたけれど。。。
(SQL Server)SQLサーバの無人インストールとインストール後の各種設定設定 Part3とかなり関連のあるネタです。


バッチファイルで SQL Server 2005 Express のインストールと mdf のアタッチさせるんですが、mdf ファイルはシステムドライブの固定のフォルダにおいてるとします。たとえば C:\test\testdb.mdf とします。

最初は下記のようにしてました。
・バッチファイル(Windows認証)

>sqlcmd -S localhost\REALSTYLE -i makeuser.sql

・SQLファイル( makeuser.sql)

CREATE DATABASE RhythmPro ON
(FILENAME = N'%systemdrive%\test\testdb.mdf' ),
(FILENAME = N'%systemdrive%\test\testdb_log.ldf' )
FOR ATTACH;


SQL ファイルの中で %systemdrive% と入れたんですが、環境変数は SQL スクリプトでは使えないようです。

ということで、下記のようにバッチファイルの中に SQL クエリを記述すると、環境変数が置換されちゃんと動きました。

>sqlcmd -S localhost\SQLEXPRESS -Q "CREATE DATABASE TestDatabase ON (FILENAME = N'%systemdrive%\test\testdb.mdf' ),(FILENAME = N'%systemdrive%\test\testdb_log.ldf' ) FOR ATTACH;"


あと、SQL Server の自動インストールバッチファイルと同じバッチファイル上でに sqlcmd コマンドを使おうとすると、ダメみたいです。
どうやら SQL Server インストール中に環境変数 Path に sqlcmd があるフォルダへのパスが登録されるっぽいですが、いったん終了して再度コマンドプロンプトを立ち上げないと、環境変数反映されないっぽいです。
ここら辺注意が要りますね。
[PR]
by jehoshaphat | 2009-07-08 00:46 | SQL | Trackback | Comments(0)