2017-08-13 77 views
1

我想寫一個Powershell腳本來將數據寫入SQLite數據庫並從中讀取數據。我正在使用PSSQLite模塊來執行此操作。該腳本在一臺服務器上工作,但不在另一臺服務器上。這兩臺機器都是Windows 2012 R2。使用Powershell和PSSqlite進行SQLite訪問 - SELECT查詢失敗

這兩款機器是這樣的:

PS C:\> $PSVersionTable 

Name       Value 
----       ----- 
PSVersion      5.0.10586.117 
PSCompatibleVersions   {1.0, 2.0, 3.0, 4.0...} 
BuildVersion     10.0.10586.117 
CLRVersion      4.0.30319.42000 
WSManStackVersion    3.0 
PSRemotingProtocolVersion  2.3 
SerializationVersion   1.1.0.1 


PS C:\> Import-Module PSSQLite 
PS C:\> Get-Module PSSQLite 

ModuleType Version Name        ExportedCommands 
---------- ------- ----        ---------------- 
Script  1.0.3  PSSQLite       {Invoke-SQLiteBulkCopy, Invoke-SqliteQuery, New-SQLiteConn... 

PS C:\> 

我有一個簡短的PowerShell腳本來創建一個SQLite數據庫,在其中創建一個表中,填寫表,然後從表中讀取。該腳本是這樣的:

Import-Module PSSQLite 
$secretsDatabase = ".\secrets.db" 

if (Test-Path $secretsDatabase) { 
    Write-Host "$secretsDatabase already exists" 
} else { 
    $create_query = "create table secrets (tid string, password string, username string)" 
    $cq_result = Invoke-SqliteQuery -DataSource $secretsDatabase -Query $create_query 

    $add_secrets_query = "insert into secrets (tid, password, username) values ('xx1', 'somepassword', '[email protected]')" 
    $as_result = Invoke-SqliteQuery -DataSource $secretsDatabase -Query $add_secrets_query 
} 

$secretsQuery = "select tid, password, username from secrets limit 1" 

$result = Invoke-SqliteQuery -DataSource $secretsDatabase -Query $secretsQuery 
Write-Host $result 

當我在一臺服務器上運行此PowerShell腳本,輸出看起來是這樣的:

PS C:\> C:\sqlite_test.ps1 
.\secrets.db already exists 
@{tid=xx1; password=somepassword; [email protected]} 

PS C:\> 

這是預期的輸出。

當我運行在其他服務器上相同的腳本,輸出看起來是這樣的:

PS C:\> C:\sqlite_test.ps1 
.\secrets.db already exists 
Unable to find type [DBNullScrubber]. 
At C:\Program Files\WindowsPowerShell\Modules\PSSQLite\1.0.3\Invoke-SqliteQuery.ps1:518 char:25 
+       [DBNullScrubber]::DataRowToPSObject($row) 
+       ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 
    + CategoryInfo   : InvalidOperation: (DBNullScrubber:TypeName) [], RuntimeException 
    + FullyQualifiedErrorId : TypeNotFound 


PS C:\> 

在兩個系統中,SQL查詢創建一個表並插入一行的作品。這是通過使用在兩臺機器上的命令行實用程序和得到這個結果證明:

C:\> sqlite3 secrets.db 
SQLite version 3.19.3 2017-06-08 14:26:16 
Enter ".help" for usage hints. 
sqlite> .dump 
PRAGMA foreign_keys=OFF; 
BEGIN TRANSACTION; 
CREATE TABLE secrets (tid string, password string, username string); 
INSERT INTO secrets VALUES('xx1','somepassword','[email protected]'); 
COMMIT; 
sqlite> 

但是一臺機器上的SELECT查詢失敗,因爲「[DBNullScrubber]」的錯誤。如何在一臺機器上糾正這個問題?

------更新:2017年8月13日更多的分析-----------------

我做了一些代碼在GitHub庫這個洞穴探險模塊,插入文件

Invoke-SqliteQuery.ps1

我走進我的PowerShell中的壞服務器上跑從該文件中的代碼片段:

$cSharp = @' 
       using System; 
       using System.Data; 
       using System.Management.Automation; 

       public class DBNullScrubber 
       { 
        public static PSObject DataRowToPSObject(DataRow row) 
        { 
         PSObject psObject = new PSObject(); 

         if (row != null && (row.RowState & DataRowState.Detached) != DataRowState.Detached) 
         { 
          foreach (DataColumn column in row.Table.Columns) 
          { 
           Object value = null; 
           if (!row.IsNull(column)) 
           { 
            value = row[column]; 
           } 

           psObject.Properties.Add(new PSNoteProperty(column.ColumnName, value)); 
          } 
         } 

         return psObject; 
        } 
       } 
'@ 

這段代碼定義DBNullScrubber類。在那之後,我去了我的命令行的不良服務器上跑:

PS C:\> Add-Type -TypeDefinition $cSharp -ReferencedAssemblies 'System.Data','System.Xml' 
Add-Type : (0) : Warning as Error: Invalid search path 'D:\Program Files\IBM\SQLLIB\LIB' specified in 'LIB environment variable' -- 'The system cannot find 
the path specified. ' 
(1) :     using System; 
At line:1 char:2 
+ Add-Type -TypeDefinition $cSharp -ReferencedAssemblies 'System.Data' ... 
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 
    + CategoryInfo   : InvalidData: (error CS1668: W...th specified. ':CompilerError) [Add-Type], Exception 
    + FullyQualifiedErrorId : SOURCE_CODE_ERROR,Microsoft.PowerShell.Commands.AddTypeCommand 

Add-Type : Cannot add type. Compilation errors occurred. 
At line:1 char:2 
+ Add-Type -TypeDefinition $cSharp -ReferencedAssemblies 'System.Data' ... 
+ ~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~~ 
    + CategoryInfo   : InvalidData: (:) [Add-Type], InvalidOperationException 
    + FullyQualifiedErrorId : COMPILER_ERRORS,Microsoft.PowerShell.Commands.AddTypeCommand 


PS C:> 

我跑這個良好的服務器上,並沒有任何錯誤。

在這一點上,我不知道該怎麼做。我怎樣才能解決這個問題?

-----------------更新2017年8月13日 - 12:11 ----------------

我打印出$ env:Lib。好機器上沒有定義。在壞機器上它說:

PS C:\> $env:Lib 
;D:\Program Files\IBM\SQLLIB\LIB 
PS C:\> 
+1

顯示'$ env:LIB'。 – PetSerAl

回答

0

運行以下操作刪除Lib環境變量。

Remove-Item $env:Lib 

更好的是,保存舊值,運行腳本,然後恢復舊值。

Import-Module PSSQLite 
$secretsDatabase = ".\secrets.db" 

$envlib = $env:Lib 
Remove-Item env:Lib 

if (Test-Path $secretsDatabase) { 
    Write-Host "$secretsDatabase already exists" 
} else { 
    $create_query = "create table secrets (tid string, password string, username string)" 
    $cq_result = Invoke-SqliteQuery -DataSource $secretsDatabase -Query $create_query 

    $add_secrets_query = "insert into secrets (tid, password, username) values ('xx1', 'somepassword', '[email protected]')" 
    $as_result = Invoke-SqliteQuery -DataSource $secretsDatabase -Query $add_secrets_query 
} 

$secretsQuery = "select tid, password, username from secrets limit 1" 

$result = Invoke-SqliteQuery -DataSource $secretsDatabase -Query $secretsQuery 
Write-Host $result 

$env:Lib = $envlib