Tuesday, December 22, 2009

Edit Oracle DMBS JOBS

oracle version: oracle 9.2
tools: OEM, sqldeveloper

今天發現oracle上一些排程的時間都莫名其妙的往後延了許多,導致影響其他系統的資料正確性,所以動工將一些固定排程的時間做個修正。

一開始理所當然的打開OEM想直接做編輯(Database => DB_NAME => Distributed => Advanced Replication => Administration => [Tab] DBMS Jobs)。結果... 我猜因為中文語系的關係,導致oracle自己一直無法解析時間參數,丟出error。

其實之前已經某一次要新增排程時就遇過這個問題了,所以只好轉戰sql developer,自己寫PL/SQL = =。不過還是一直有一些細節沒注意到,try了好幾次才ok。

首先要注意的是,一定要是該job的owner才有辦法修改他,就算是dba也不行= =! 以DBA身分查詢"DBA_JOBS"這個view,的確可以看見所有已經在系統內的排程,但若是查詢"USER_JOBS"這個view,會發現沒有東西,以DBA身分去修改屬於別人的JOB時,會遇到"ORA-23421"的錯誤,說明如下:

ORA-23421: job number string(%s) is not a job in the job queue
Cause:There is no job visible to the caller with the given job number
Action:Choose the number of a job visible to the caller

所以,請先確定是用該JOB的owner登入資料庫,此時再去查詢"USER_JOBS"可看見屬於他的排程。
接下來要做的是: "修改"已經存在的排程,這邊不討論新增o刪除。

   1:  begin dbms_job.change(

   2:      job => 777, 

   3:      next_date=>to_date('1-1-2010 00:00:00', 'dd-mm-yyyy hh24:mi:ss'),

   4:      interval=> '/*Each Month*/ Add_months(sysdate, 1)',

   5:      what=>

   6:          '--Your PL/SQL here:

   7:          Declare

   8:              v_year number(4);

   9:              v_month number(2);

  10:              v_day number(2);

  11:          begin

  12:              v_year := to_number(to_char(sysdate,''YYYY''));

  13:              v_month := to_number(to_char(sysdate,''MM''));

  14:              v_day :=to_number(to_char(sysdate,''DD''));

  15:   

  16:              --call pre-defined store procedure

  17:              my_store_procedure(v_year, v_month, v_day);

  18:          end;'

  19:  );

  20:  end;

就先從... "修改"說起吧,如Line #1所見,請使用change。
  1. job: job number, user jobs這個view裡的job欄位
  2. next_date: 下次執行時間
  3. interval: 執行頻率,多久執行一次
  4. what: 排程內容(通常是執行某個store procedure,如Line #17)
請注意以上除了job以外,他們的值都有放在一對單引號(' ')裡面!

其餘部分:
Line#4:/*Each Month*/ 這是註解= =
Line#17: 是此排程最主要要執行的store procedure,但因為他需要其他參數,所以有一些前置作業(Line #12~ Line #14)先來取得這些參數
Line#12:這邊要特別注意的是!!!! to_char這個函式原本其實只要寫成這樣: to_char(sysdate, 'YYYY') 就好(就是他的format只要放在單引號內),但是因為這些what語法已經先放在一對單引號內了,如果這邊使用單引號會讓資料庫以為這是what內容的結尾,所以必須在每個單引號前面再加上一個單引號!!! Line #13, Line #14同理

以上,大概是全部要注意的地方了~

Monday, December 21, 2009

[Study] Maintaining Tablespaces and Data Files

這章拖超久的= = 距上次大概一個月了吧!!!
讀到最後一點都不想整理PPT了,只好給他草草了事orz..


Friday, December 11, 2009

Get the display value of DropownDatawindow

如題。

PowerBuilder 裡有一個相當方便的東西就是dropdowndatawindow(dddw)。要取到他的值(data value)很容易,但是要抓到顯示的值(display value)倒是第一次。

displayValue = dw_1.Describe("Evaluate('LookUpDisplay(column_name) ', row#))

一行搞定XD 不過裡面用了很多東西= =。


LookUpDisplay
DescriptionObtains the display value in the code table associated with the data value in the
specified column.
SyntaxLookUpDisplay(column)
Return ValueString. Returns the display value when it succeeds and the empty string (“”) if
an error occurs.


Evaluating DataWindow expressions in the Describe function
DescriptionThe Describe function provides a way to evaluate DataWindow expressions outside their usual context.
Syntaxdwcontrol.Describe ("Evaluate ( 'expression' , rownumber ) " )


Tuesday, December 01, 2009

ARCn: Log actively being archived by another process

今天去關心我親愛的資料庫時,發現他在凌晨兩點相當勤奮的狂丟archive log出來= = 行為相當怪異,所以就去翻翻alert log看看是否有怪訊息,看看似乎也沒什麼error,就是在那個時間相當密集的出現如下訊息:

ARCn: Beginning to archive log# 2 thrd# 1 seq# 24
ARCn: Unable to archive log# 2 thrd# 1 seq# 24
Log actively being archived by another process

嗯... what happened XD?!
再Ask Tom裡找了一些相關文章,其中有某篇算是回答了我的問題:
It is just a side effect of having more then one archiver.

If automatic archiving is turned on then all of the archiver process will try to archive this logfile, however they will not be able to aquire the lock 'kcrrlt', the lock to protect multiple arch processes from archiving the same logfile.

The failing process process will write to the trace/alert message that it was unable to archive the logfile.

The file is successfully archived by some other process.


嗯... 所以其實好像,也沒什麼XD,後來我發現這樣的訊息一直都會出現啦~ 只是沒有像今天凌晨一直連續出現。所以其實問題應該是... "凌晨兩點幹嘛一直勤勞的丟log!? 是誰一直在用系統@_@!?" 這樣XD

好哩~ 這個問題就到這邊。原本看了一些文件想整理一下,不過現在好懶= = 就先這樣吧~ :P

Ref:
Monday, November 16, 2009

[Study] Maintaining Redo Log Files



Friday, November 06, 2009

WSS 3.0 Open links In New Window

這兩個禮拜一直在替WSS換長相,摸出了一些心得。不過今天不講這些XD
講一下WSS的超連結,預設行為都是開在同一個頁面,但是對於那些專門做連結的清單、或是就是要另開新視窗的連結而言,若無法改變WSS行為,操作起來就相當麻煩。

Entonces, 該如何設定讓WSS的特定頁面的超連結行為為開新視窗呢?
  1. 移駕至該頁面
  2. 點選右上角"網站動作" > "編輯頁面" > "新增網頁組件"
  3. 選擇"內容編輯器網頁組件" > 新增
  4. 組件新增至頁面上後,點選內容的"開啟工具窗格"
  5. 點選"原始檔編輯器...",會跳出一個空白對話框,在裡面貼上以下程式:

       1:  <script language="JavaScript">

       2:   

       3:  //add an entry to the _spBodyOnLoadFunctionNames array

       4:  //so that our function will run on the pageLoad event

       5:   

       6:  _spBodyOnLoadFunctionNames.push("rewriteLinks");

       7:   

       8:  function rewriteLinks() {

       9:   

      10:       //create an array to store all the anchor elements in the page

      11:       var anchors = document.getElementsByTagName("a");

      12:   

      13:       //loop through the array

      14:   

      15:       for (var x=0; x<anchors.length; x++) {

      16:       //does this anchor element contain #openinnewwindow?

      17:   

      18:            if (anchors[x].outerHTML.indexOf('#openinnewwindow')>0) {             

      19:               //store the HTML for this anchor element

      20:               oldText = anchors[x].outerHTML;

      21:                

      22:               //rewrite the URL to remove our test text and add a target instead

      23:               newText = oldText.replace(/#openinnewwindow/,'" target="_blank');

      24:   

      25:               //write the HTML back to the browser              

      26:               anchors[x].outerHTML = newText;

      27:            }

      28:       }

      29:  }

      30:   

      31:  </script>


  6. 儲存後,另外在"版面配置"區段下將"隱藏"方框勾選起來即可套用,並結束編輯頁面。
  7. 最後,針對該頁面需要在新視窗開啟的超連結網址後面全部加上"#openinnewwindow"即可!!!
稍微說明一下上面那段javascript主要在做什麼:
首先,第7點說的在網址後面加上"#openinnewwindow"字樣其實是跟程式互相配合的,行18即是尋找所有超連結網址裡是否有這個字樣,如果有找到,就把他換成" target=_blank"這樣而已XD 所以有該字樣的 <A>tag行為就會變成以新視窗開啟了~


Monday, October 26, 2009

[Study] Maintaining the Control File

內容相當薄弱的一個章節... 關於oracle control file


Tuesday, October 20, 2009

[Study] Data Dictionary Content and Usage



Monday, October 12, 2009

[Study] Creating a Database

1. 介紹OMF
2. 利用create database指令手動建立一個oracle資料庫(OMF)


Wednesday, October 07, 2009

Request Cert Without IIS(Server2008) and Config Reporting Server 2008 using SSL

吼!!!!!!!!!!!!!!!!!!!!! 搞了兩個多禮拜!!
記錄一下
  1. 怎麼利用Certreq.exe工具產生一個憑證要求,再利用此*.req向內部憑證核發單位要到憑證。這是完全不透過IIS要求憑證的做法。
  2. 設定讓Reporting Service也能使用安全性連線(https://XXX/ReportServer)
之前將SQL Server從2005整個異機升級到2008(here),2008的report server號稱不再依靠IIS就可以運作,好是好,但是我要做安全性連線阿!!! 一直以來只知道怎麼用IIS要求憑證,現在既然沒IIS了... 也不想因為一個憑證就架起來,文件也說IIS 和 Reporting Services 安裝在同一部電腦上會影響報表伺服器的SSL連線(here),只好開始研究怎麼不靠IIS取得憑證。

利用Certreq.exe
  1. 先產生一個*.inf,待會配合certreq -new要用的,*.inf內容如下:
    抱歉我無法解釋這個東西.....
    (subject內CN=" "內需改成完整電腦名稱)

  2. [NewRequest]
    Subject = "CN=host.domain.com"
    KeySpec = 1
    KeyLength = 1024
    Exportable = TRUE
    MachineKeySet = TRUE
    UseExistingKeySet = FALSE
    ProviderName = "Microsoft RSA SChannel Cryptographic Provider"
    ProviderType = 12
    RequestType = PKCS10
    KeyUsage = 0xa0

    [EnhancedKeyUsageExtension]
    OID=1.3.6.1.5.5.7.3.1


  3. 系統管理員身分開啟命令提示字元(cmd),切換到剛剛產生的inf檔資料夾下,假設剛剛存的檔案為certReq.inf。用下面指令產稱一個*.req檔
    > certreq -new certReq.inf certReq.req

    完成後系統會回覆: CertReq: Request Created
    在同層資料夾下可以看見剛剛產生的certReq.req

  4. 以記事本開啟此certReq.req,可以看見一堆像亂碼的文字放在
    "-----BEGIN NEW CERTIFICATE REQUEST-----" 跟
    "-----END NEW CERTIFICATE REQUEST-----" 兩段文字中間,
    整個內容copy下來,接下來的步驟就比較熟悉了。

  5. 開啟內部核發憑證的伺服器 http://serverName/certsrv
    依序點選: 要求憑證 > 提交進階憑證要求 > 用 Base-64 編碼的CMC或PKCS #10檔案來提交憑證要求,或用Base-64編碼的PKCS #7檔案提交更新要求。
    最後將剛剛copy的整串字貼上,點選"提交 >", 最後將憑證下載回來。





  6. 開啟MMC(run> mmc),打開憑證嵌入式管理單元(電腦帳戶),如下:







  7. 剩下就給他"下一步","確定"之類的完成。

  8. 在"個人"那一層匯入剛剛取得的憑證:



  9. 完成!!!! 只完成憑證的部分= =b
設定Reporting Server 使用SSL連線
(... 好懶的寫了) 其實就是照著文件Ref#1 做就行了,但是之前憑證裝好,照著步驟做完設定之後,還是無法以https連上reportServer... 關鍵在當初申請憑證時的名稱... 似乎需要使用完整電腦名稱,這個東西小小的寫在Reporting Services組態管理員的help裡...



Ref:
Tuesday, October 06, 2009

[Study] Managing an Oracle Instance

本章有四個重點: parameter file, startup instance, shutdown instance, diagnostic files


PBDWN105.DLL

前幾天準備將一個web application(其中當然有用datawindow.net開發的東西)搬到另一台新機器上,測試時就遇到這個問題:

Exception Details: Sybase.DataWindow.DataWindowServerLoadFailedException: DataWindow Server PBDWN105.DLL not found.

這個... 好吧。原文解法請參閱reference。
以下為簡易說明:
  1. 在開發機器或可以執行該datawindow的機器上,找到Sybase安裝位置下的"DataWindow .NET 2.0"資料夾
  2. 沒有意外的話,應該是X:/Program Files/Sybase/DataWindow NET 2.0/
  3. 在該資料夾下面可以找到一個dwpack20.exe的執行檔
  4. 執行畫面如下:


  5. 因為我的application不是WinForm,所以選擇WebForm。其他詳細說明請見reference。
  6. 完成之後會有一個msi封裝檔,把執行datawindow.net元件所需要的東西都封裝好了
  7. 把這個檔案(DWCLTRT20.msi)搬到新機器上安裝。
  8. 最後記得重新啟動IIS即可!!

Ref:

Thursday, September 24, 2009

Reporting Server 2005 異機升級至2008

前陣子做了WSS的SQL SERVER搬家兼升級(2005 to 2008_x64)作業,可是不知道為什麼,搞了很久一直沒辦法好好的把reporting server一起弄過去,裡面有幾張報表,不過都是去撈Oracle資料庫的資料。

遇到的主要問題是:
1. 資料庫部分備份出來後,還需要備份加密金鑰,可是還原的時候加密金鑰的密碼一直打不過XD
2. 新主機上明明就裝了oracle client,可是測試報表時一直抱怨無法連接資料庫,用sqlplus又可以連

因為一直搞不定,所以就擱著不理他,沒想到上禮拜心血來潮找到了一篇相關的文章,照著做就成功了!! 可是該做的當初明明都做過XDD 整個莫名其妙~

moving reporting server 2005 to reporting server 2008
  1. 分別備份ReportServer與ReportServerTempDB兩個資料庫,用SQL Server Management Studio做就行了,步驟就不描述
  2. 開啟"Reporting Services組態管理員"(Microsoft SQL Server 2005>組態工具 下),點選"加密金鑰"頁籤,將加密金鑰備份出來
  3. 到新主機(SQL Server2008)上,利用"SQL Server Configuration Manager"(Microsoft SQL Server 2008>組態工具 下) 將Reporting Service服務停止
  4. 用SQL Server Management Studio分別還原ReportServer與ReportServerTempDB兩個資料庫(Restore With Recovery),步驟略
  5. 同步驟3,再將Reporting Service服務開啟
  6. 開啟"Reporting Services組態管理員"(Microsoft SQL Server 2008>組態工具 下)將金鑰還原
  7. 完工!!
Oracle client的部分真的是沒理他,也沒重開機,自己就忽然可以動了= = 就這樣~

Ref:

Tuesday, September 22, 2009

[Study] Getting Started With the Oracle Server

這一張主要介紹一些圖形管理介面、sqlplus,還有最重要的,password file。


[Study] Oracle Architectural Components

幾個禮拜前讀的,因為present需要,所以做成ppt。
然後又相當自戀的覺得內容很棒XD 所以分享一下。


Thursday, September 10, 2009

Oracle - Alert log

今天讀到Monitor Diagnostic Files這塊。忽然想起來,之前把資料庫搞掰咖之後,一直沒發現,就是因為我從排程器裡看他都回報備份有正常結束(0x0)。

真正detail的訊息還是得靠oracle自己的trace file們。果然,再回去找alert log,果然就看到一些相關訊息。


先來介紹一下trace file。

Each server and background process can write to an associated trace file. When an internal error is detected by a process, it dumps information about the error to its trace file.

The alert file, or alert log, is a special trace file. The alert file of a database is a chronological log of messages and errors, which includes the following:

  1. All internal errors (ORA-600), block corruption errors (ORA-1578), and deadlock errors (ORA-60) that occur
  2. Administrative operations, such as CREATE, ALTER, and DROP statements and STARTUP, SHUTDOWN, and ARCHIVELOG statements
  3. Several messages and errors relating to the functions of shared server and dispatcher processes
  4. Errors occurring during the automatic refresh of a materialized view
  5. The values of all initialization parameters at the time the database and instance start

Oracle uses the alert file to keep a log of these special operations as an alternative to displaying such information on an operator’s console (although many systems display information on the console). If an operation is successful, a "completed" message is written in the alert file, along with a timestamp.


這些trace files的位置分別記錄在兩個parameter裡:

BACKGROUND_DUMP_DEST: trace file for background processed, alert file

USER_DUMP_DEST: trace file for server process

要看這些parameter的值可用slqplus下> show parameter <parameter_name>


好! 所以我就去把alert file挖出來,找到事發當時的時間,觀察一下系統在某個datafile offline的狀態下還要做hot backup(alter  tablespace begin backup...) 時揪竟會怎樣。真相來了:

alter tablespace XXX begin backup
ORA-1128 signalled during: alter tablespace AP begin backup... 
alter tablespace XXX end backup
ORA-1142 signalled during: alter tablespace AP end backup...


果然就是有問題啦。順便查了這兩個錯誤訊息,分別如下:

ORA-1128
Description: cannot start online backup - file string is offline
Cause: An attempt to start an online backup found that one of the files is offline

ORA-1142
Description: cannot end online backup - none of the files are in backup
Cause: None of the files were found to be in online backup when attempting to end an online backup

完畢!!


Use batch file to backup(copy) files by date

利用Oracle 11g 做了每周系統全備份與每日export檔、設定archive的丟出。丟出來的檔案自己依日期分別放在一個一個資料夾內,為了做異地備份,需要每天、每周去copy出這些檔案,而且是copy到異地硬碟內,不是本機其他硬碟上(特別強調是因為會影響到寫法與執行成功與否)。所以寫了一個batch file,並且設定排程來執行工作。

首先在要放batch file的同層目錄下放一個文字檔(copy_msg.txt),用來記錄copy過程訊息用。

batch file內容如下:


   1:  rem //rem 表示註解,command line會忽略此行

   2:  rem "echo.": 表示印出一行空白

   3:  rem ">>"   : 將echo的內容以"附加"方式寫入copy_msg.txt檔內

   4:  rem 執行batch file第一件事: 顯示日期時間

   5:  echo. >> copy_msg.txt

   6:  echo start copy ARCHIVELOG at %date% %time% >> copy_msg.txt

   7:   

   8:  rem 切換到copy_msg.txt所在目錄下

   9:  cd \

  10:  e:

  11:   

  12:  rem 先將日期format為oracle丟出來的格式: yyyy_mm_dd,並且存在today變數內

  13:  set today=%date:~0,4%_%date:~5,2%_%date:~8,2%

  14:  echo folder name = %today% >> copy_msg.txt

  15:   

  16:  rem 印出開始做copy的訊息

  17:  echo start copying... >> copy_msg.txt

  18:   

  19:  rem 利用xcopy做複製,帶I參數,表示若目的資料夾不存在,自動產生

  20:  rem 同時將copy訊息都寫入copy_msg.txt

  21:  xcopy X:\<source_path>\%today%\* \\<target_server>\<target_path>\%today% /I >> copy_msg.txt

  22:   

  23:  rem 完成後也印出提示訊息

  24:  echo task end at %date% %time% >> copy_msg.txt

  25:  echo **************************************************************** >> copy_msg.txt

  26:  exit

完成!! 若執行過一次,可以去看copy_msg.txt內容大概長這樣:

start copy ARCHIVELOG at 2009/09/09 星期三 23:59:00.30
folder name = 2009_09_09
start copying...
X:\<source_path>\2009_09_09\O1_MF_1_3689_5BF3H8FR_.ARC
X:\<source_path>\2009_09_09\O1_MF_1_3690_5BF3NLXR_.ARC
X:\<source_path>\2009_09_09\O1_MF_1_3691_5BFQT2CF_.ARC
複製 3 個檔案
task end at 2009/09/09 星期三 23:59:09.61
****************************************************************
這樣就可以達到每天自動複製不同資料夾內的檔案之工程了~
Friday, September 04, 2009

What is Oracle RAC?

Oracle RAC(Real Application Clusters)
DEFINITION - Real Application Cluster (RAC) is a component of the Oracle 9i database product that allows multiple computers to run Oracle RDBMS software simultaneously while accessing a single database, thus providing a clustered database.

According to Oracle, RAC's shared disk method of clustering databases:
increases scalability: because servers can easily be added or subtracted to meet current needs
lowers costs: because companies don't have to buy high-end servers
improves availability: because if one server fails, another can assume its workload.

In a non-RAC Oracle database, a single instance accesses a single database. Where the "database" consists of a collection of data files, control files, and redo logs located on disk; the "instance" comprises the collection of Oracle-related memory and operating system processes that run on a computer system.

In an Oracle RAC environment, two or more computers (each with an instance) concurrently access a single database. This allows an application or user to connect to either computer and have access to a single coordinated set of data.

RAC's shared disk architecture is an unusual approach to database clustering. Most competing database products (such as Microsoft's SQL Server and IBM's DB2 for Windows and Unix environments) use the alternative, which is known as "shared nothing" architecture. Shared nothing architecture partitions data and only gives each server access to its own disk subsystem, while shared disk architecture gives all servers access to the entire database. This adds failover capacity to the database, because all servers have access to the whole database.

Cluster
A computer cluster is a group of linked computers, working together closely so that in many respects they form a single computer. The components of a cluster are commonly, but not always, connected to each other through fast local area networks. Clusters are usually deployed to improve performance and/or availability over that provided by a single computer, while typically being much more cost-effective than single computers of comparable speed or availability.

Ref:
Thursday, September 03, 2009

前陣子(從把資料庫搞掰咖之後,又剛好遇到SQL資料庫要搬家)諸事不順,陸續看了一堆文件都沒空document一下。先記著,以後"有機會、有心力"再補XD。
  1. Windows SharePoint Service(WSS3.0)之資料庫搬家順便升級(2005=>2008)
  2. Oracle 9i: drop one datafile from tablespace
  3. Oracle 9i: control file
  4. Oracle 9i: autorun offline backup script
  5. Oracle 9i: OS授權?
  6. PowerBuilder: cross table, printpreview

What is CULV?

看到這個詞也有一陣子時間了,之前還特地去查過到底是什麼鬼,但是該看的看過一遍,還是無法具體一點講出到底何為CULV?! (我想跟個人表達能力也有點關係= =a) 今天又在癮科技看到這個詞,都有打算換台筆電了,也該好好來認識他一下。
以下剪剪貼貼一些文章片段:

CULV(Consumer Ultra Low Voltage)
CULV處理器嚴格來說不是全新的技術,早在多年前Pentium、Celeron時期就已有LV(Low Voltage)低電壓版處理器、以及ULV(Ultra Low Voltage)超低電壓版處理器。

ULV超低電壓版處理器除了用在上述輕薄筆電(Ultra Slim NB)外、也大量運用於嵌入式系統和手持裝置如UMPC超行動電腦。ULV處理器其實是Intel專為刀鋒伺服器、嵌入式系統和輕薄筆電打造的處理器,是專為體積狹小、散熱空間不足等嚴苛環境所設計。

ULV處理器作法能減輕體積厚度,讓筆電體積更薄,再加上散熱佳、以及低功耗的省電訴求,理所當然受到輕薄筆電愛戴。為了提振常規筆電的買氣,英特爾(Intel)將過往僅用於嵌入式系統、超薄型(Ultra Slim)筆電的超低電壓版(Ultra Low Voltage;ULV)處理器,以較低價格供應筆電業者,並允許用於消費性(Consumer)筆電上,此被稱為CULV NB。

CULV NB的效能優於使用凌動(Atom)處理器的小筆電,且相關規格比照常規筆電,如11、12吋以上的顯示器尺寸,具備光碟機、ExpressCard槽等,但價位、功耗卻低於常規筆電,此成為筆電業者於2009年第2季開始的主攻產品。

以上是一些簡單介紹,若要知道其他與Atom比較的小消息或是CULV定位等,請見reference。
<(_ _)>

Ref:
Wednesday, September 02, 2009

ORA-12560: TNS:protocol adapter error

昨天在測試資料庫上要針對一個user做import。
直接在command line裡下>imp後,接著打帳號密碼,就遇上這個問題。
大概知道是什麼問題,還是找個文件來看一下:

Cause:
Oracle classify this as a ‘generic protocol adapter error’. In my experience it indicates that Oracle client does not know what instance to connect to or what TNS alias to use.

因為這台server上裝了三個資料庫,下imp前需先指定是針對哪個資料庫做的操作:
>set oracle_sie=oracle_sid
就這樣,搞定。

Friday, July 31, 2009

Simplify the result of Blog Search and Tags

詳細描述目標:
使用blogger提供的search功能或是Tags(label)功能時,有時候因為資料量大、篇幅大,比較希望可以只列出標題就好。

這真是個好主意,花十分鐘就可以搞定了。
所以請自行參閱Reference

Ref:
標籤/搜尋頁面只列出標題 (Simplify the result of label and search)

Thursday, July 23, 2009

"Performance counter registry hive consistency check" while installing SQLServer 2008

昨天在一台"全新"的WinServer 2008上準備安裝SQL 2008,前面會先進行一些檢查,結果還是遇到一些問題。主要是下面這一項無法通過檢查:
效能計數器登錄區一致性失敗(英文版的訊息如title)

點選後可以看見詳細"一點點點點"的訊息如圖:

勤勞一點的人可能就會循著訊息給的網址去一探究竟,是一篇主要教你做三個動作的文章:
  1. Rebuild the base performance counters
  2. Re-add the extensible counters
  3. Reinstall any custom .NET Framework assembly performance counters
它有英文版中文版,強烈不建議看中文版XD 機器翻的超奇怪。不過說真的,這篇文章對我個人似乎沒什麼幫助,相當遺憾。

先來說說這個訊息到底是要表達啥鬼好了。中文的話,了解了之後跟字面上的意思的確滿接近的XD,登錄區指的就是註冊表... 裡面有某些值因不明原因變的不一樣了,that's all.
根據 Ref #1 裡的敘述就是這兩對值:

HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Perflib
下的Last Counter還有Last Help
HKEY_LOCAL_MACHINE\SOFTWARE\Microsoft\Windows NT\CurrentVersion\Perflib\009
下的Counter還有Help(這兩個是多字串值,分別看他們最後一組數字)

其實我看到90%的文章都說只要以 ...\Perflib\009這組值為準,把 ...\Perflib的Last Counter還有Last Help改成一樣就好。但是大家都不說,前提是你的作業系統是英文版的... = =
其實我的 ...\Perflib底下不只有\009還有一個\0404,但是\0404裡只有一個(預設值),沒有Counter跟Help,於時我就試著在\0404下替他新增這兩個多字串值,內容跟...\Perflib\009的一樣。就搞定了...

順便聊聊,很多人的中文版好像不是\0404而是\004,超奇怪的= =,我一直不知道這個數字是哪裡來的,不過有看到其他人再教怎麼找出這個數字(請參閱Ref #2)。只要隨便開個console程式,跑一行程式即可。

string str2 = string.Format("{0,3}", CultureInfo.InstalledUICulture.Parent.LCID.ToString("X")).Replace(" ", "0");
跑出來的數字就是所謂的LCID(Locale ID),請見Ref列表,而0404就是Chinese - Taiwan。

以上~ 下台一鞠躬。

Ref:
Tuesday, July 07, 2009

Mount VirtualBox's share folder in Linux

又浪費了半天!!真是不懂, 別人都可以輕輕鬆鬆過關的東西, 我就要東翻西找其他解法才可以Q口Q
這次呢... 是我想在架在虛擬機器上的ubuntu裡看一份文件, 不想再host 和guest間切換來切換去就對了, 想說應該有辦法抓到本機(winXP)檔案吧。
那麼,就直接來八。
  1. 啟動虛擬機器後,在該機器〝VirtualBox〞視窗的選單上有〝裝置(D)〞,如圖。特地附上這個圖是因為當初在某篇文章上看到裝置兩個字… 我找半天也找不到這個選單… = = 原來指的是這個。

  2. 視窗開起來後如下,自行指定路徑與資料夾名稱,請記得這個名字,後面要用到。
  3. 回到Ubuntu(guest環境),新增一個資料夾在喜歡的地方,ex︰
    >sudo mkdir /mnt/ShareDoc
  4. 以上大概都不會有什麼問題,重頭戲在掛載資料夾這一步!就是把第二步驟新增的資料夾掛到虛擬機器上來用。
    >sudo mount-t vboxsf [shareFolderName] [mountPoint]

    shareFolderName: 第二步驟新增的資料夾名稱
    mountPoint: 第三步驟新增的資料夾路徑
    到這裡照理說就結束了。
我們可以將人類分成兩群:幸福的跟不幸福的XD。不幸福的就跟我一樣,會有詭異的錯誤,而我遇到的是這個:
"mount.vboxsf: mounting failed with the error: Protocol error"
如果你也跟我一樣,可以嘗試改下這個command:
>sudo mount.vboxsf [shareFolderName] [mountPoint]

我說可以嘗試,是因為在我找到這個解法之前,其他人都沒有提供這個方法… 不然就是寫一些看無的東西… 所以,這裡可以判斷你是不是屬於不幸中的不幸XDDDD

如果改下command還是無法掛載成功… 可以先參考提供的reference,如果沒頭緒,請自行找其他文件xD

最後,如果要每次開機就自動掛載,請參閱ref#3。因為我目前還沒有需求所以也還沒設定,所以無法判斷自己是不是幸福人xD。等哪天我發現自己真的很不幸再來補作法。

Ref:
  1. VirtualBox-Linux mount share folder
  2. Share folder with virtualbox -- just a short note
  3. 電腦技術:: Mount VirtualBox's shared folders in linux

TrueType造字程式

研究了兩個半天,終於稍微釐清了這東西的一些概念。
不過現在不想寫XD。
隨文附上一個好東西: Microsoft EUDC Deployment Tool
自行研究。
Monday, July 06, 2009

Database maintenance for WSS3.0

Ref:
Wednesday, July 01, 2009

Ubuntu: moving file

連個簡單的剪下貼上都不會用Q口Q
For MOVING:
>sudo mv [file] [dest_path]

For COPYING
>sudo cp [file] [dest_path]

For Create New File
>sudo mkdir [folder_path]

Changt root password
>sudo passwd root

Delete an Folder with contents
>sudo rm -rf [folder_path]


Install MySQL
>sudo apt-get install mysql-server mysql-client

Install Mongrel
After installed rails on Linux, you'll find the default web server is WEBrick, to use Mongrel:
>sudo gem install mongrel

Install .deb File
>sudo dpkg -i [file.deb]


Use MySQL Prompt
mysql -uroot -p
Tuesday, June 30, 2009

Installing Ruby on Rails on Ubuntu

Ref:
  1. Installing Ruby on Rails on Debian/Ubuntu
  2. Debian / Ubuntu Linux 的 Ruby on Rails 環境架設

Chorme in Ubuntu
  1. Install google chrome with wine in Ubuntu
  2. How to Install Chromium (Google chrome) in Ubuntu using deb package
Friday, June 26, 2009

Convert Ruby code to HTML code for blog posting

本篇前傳請看Here

直接進入主題,首先,要先安裝一個叫syntax的東西(原諒我稱呼他為"東西" 因為我才讀ruby第二天Q口Q)
安裝的方法是透過command line下:

>gem install syntax

執行畫面如下:


安裝完成後就可以來.... 寫formatter程式XD,說寫,其實是剪剪貼貼啦XD 對程式的部分一知半解的。

程式內容如下:
################
## ruby2html.rb
################

require "rubygems"
# "rubygems" 少了就被抱怨:
#`require': no such file to load -- syntax/convertors/html (LoadError)
require "syntax/convertors/html"
require "Win32API"
require "Win32/clipboard"
include Win32
# 上面這行少會被被抱怨:
#undefined method `data' for Windows::Clipboard:Module (NoMethodError)

in_data = Clipboard.data
convertor = Syntax::Convertors::HTML.for_syntax "ruby"
code_html = convertor.convert(in_data)
Clipboard.set_data(code_html)
以上算是try and error來的XD,我也不知道為什麼別人的程式可以跑,我就要修修改改的。
我把檔名存成"ruby2html.rb"丟在/rails_app/下面。
這支程式是這樣用的: 把要format的code選起來按複製,接著就run剛剛存好的程式:

>ruby ruby2html.rb

跑完後command line不會show什麼訊息,這時候只要開個notepad起來按貼上,就可以看到處理好的html code,就完成啦~

最後,還是要配合CSS,CSS的部份我也自己做了些修改,因為之前已經先有一段跟C#有關的CSS,怕兩種code的CSS會互相影響,以下是我的CSS file:
/* ------------------------- For format ruby codes --------------------------*/
.ruby, .ruby pre {
background-color: #f1f1f3;
color: #112;
padding: 5px;
font-family:"bitstream vera sans mono",monaco,"lucida console","courier new",courier,serif;
font-size: 0.9em;
overflow: auto;
margin: 4px 0px;
width: 95%;
}

/* Syntax highlighting */
.ruby .normal {}
.ruby .comment { color: #005; font-style: italic; }
.ruby .keyword { color: #A00; font-weight: bold; }
.ruby .method { color: #077; }
.ruby .class { color: #074; }
.ruby .module { color: #050; }
.ruby .punct { color: #447; font-weight: bold; }
.ruby .symbol { color: #099; }
.ruby .string { color: #944; background: #FFE; }
.ruby .char { color: #F07; }
.ruby .ident { color: #004; }
.ruby .constant { color: #07F; }
.ruby .regex { color: #B66; background: #FEF; }
.ruby .number { color: #F99; }
.ruby .attribute { color: #5bb; }
.ruby .global { color: #7FB; }
.ruby .expr { color: #227; }
.ruby .escape { color: #277; }
/* -----------------------------------------------------------------------*/

嗯,有了CSS跟html code配合起來,就可以把ruby code漂漂亮亮的顯示出來囉~
另外如果覺得每次都用複製code去做很麻煩的話,也可以format整個.rb檔,請自行參閱Ref 4號,個人因為習慣copy片段,所以這個是比較適合自己的方法。

Ref:
  1. Howto format ruby code for blogs (這篇應該算始祖吧..)
  2. Formatting Ruby and HTML code for blog posting
    (這篇參考始祖可以跑... 我參考他就不行跑Q口Q)
  3. syntax ruby code to html in gnome (這篇是成功的關鍵XD)
  4. Syntax Highlighting (一樣的東西,不過他讀整個.rb檔)

ruby code format test

天哪!! 我成功了!! 原本是想說開始學ruby了,也應該像C# code一樣去找個formatter來用,這樣以後要貼code比較好看,結果找來找去,好像ruby本身就提供把code轉成html tags的function!! Ruby真的是programmer的好朋友!!!
in_data = Clipboard.data
convertor = Syntax::Convertors::HTML.for_syntax "ruby"
code_html = convertor.convert(in_data)
Clipboard.set_data(code_html)

過程還是有點卡XD 晚點整理好再來分享~
Wednesday, June 24, 2009

Crystal Report資料存取模式 與 TableLogOnInfo

存取模式詳細說明請見reference。下面只節錄簡易說明:

Crystal Report提拱兩種資料存取模式:
  1. 提取模式
    由報表引擎直接向資料庫提取資料。包括連線還有SQL都由Crystal Report處理。
  2. 推入模式
    由開發人員自行撰寫連接資料庫與撈資料部分,再將資料結果(通常是DataSet)推入報表引擎,再顯示於報表。
當使用提取模式時,就需要另外處理報表連接資料庫時所需要的帳號密碼問題。因為安全考量,Crystal Report並不會記憶連接資料庫的帳號密碼。TableLonOnInfo就是提供來處理這個問題的。

   1:  protected void ConfigCrystalReport(){

   2:      TableLogOnInfo logOnInfo = new TableLogOnInfo();

   3:   

   4:      //load report

   5:      ReportDocument reportDoc = new ReportDocument();

   6:      reportDoc.Load(Server.MapPath("rpt_name.rpt"));

   7:   

   8:      //set up connection info for each table in report

   9:      //if the report connect to not only one table in db

  10:      foreach (CrystalDecisions.CrystalReports.Engine.Table table 

  11:               in reportDoc.Database.Tables)

  12:      {        

  13:          logOnInfo = table.LogOnInfo;

  14:          

  15:          //抓取config檔裡 <AppSettings>區段內設定好的資料

  16:          //除了下面列出的UserID, Password, 還可設定ServerName, DatabaseName

  17:          logOnInfo.ConnectionInfo.UserID = 

  18:                    ConfigurationManager.AppSettings["_UserId"];

  19:          logOnInfo.ConnectionInfo.Password =

  20:                    ConfigurationManager.AppSettings["_Password"];

  21:   

  22:          // apply settings

  23:          table.ApplyLogOnInfo(logOnInfo);

  24:      }

  25:  }


Ref:
Tuesday, June 16, 2009

Use validator and client script at the same time

ㄟ~ 故事是這樣的。
寫web最怕的就是連線不穩定,好死不死我寫的某塊功能就是專給海外的人處理資料用的。最近使用者跟我反應存檔後跑出兩筆一模一樣的資料.... 根據我推論,應該是因為網路剛好不穩,使用者按了submit以為沒反應又按了一次... 網路不穩歸不穩,兩次request還是都處理了。
就是這樣,所以要想辦法防止這次的request完成前再送一次。

聽起來超簡單,就按一下submit的時候把按鈕disable,複雜一點的,按一下之後先跟使用者做個確認,確定了再disable。
嗯,沒錯。就這樣,reference都不完全符合我要處理的狀況,不過頗有參考價值。
還是自己搞定了Q口Q

首先,原本寫在LinkButton上的onClientClick就不能直接寫了,因為需要多一層判斷,所以要在程式裡動態幫他把attribute加上去。

   1:  <!--原本在html裡的client confirm不能用-->

   2:  <asp:LinkButton runat="server" ID="lbSave" CommandName="save" Text="Save"

   3:  CommandArgument='<%#DataBinder.Eval(Container,"RowIndex")%>'

   4:  OnClientClick="return confirm('Are you sure?');">

   5:  </asp:LinkButton>

   6:   

   7:  <!--拿掉後: -->

   8:  <asp:LinkButton runat="server" ID="lbSave" CommandName="save" Text="Save"

   9:  CommandArgument='<%#DataBinder.Eval(Container,"RowIndex")%>'>

  10:  </asp:LinkButton>



我在Gridview資料繫結時才去幫他加上onclick的屬性:

   1:  //加上onclick attritube, 叫用lockBtn的script

   2:  ((LinkButton)GridView2.Rows[i].FindControl("lbSave"))

   3:  .Attributes.Add("onclick", "return lockBtn(this);");



script在這:

   1:  <script language="javascript" type="text/javascript">

   2:      //lockBtn: 接受觸發者當參數

   3:      function lockBtn(btn){    

   4:          //先判斷是否已disable,因為linkBtn就算disable了(會變灰色)

   5:          //但是click一樣會觸發script

   6:          if(btn.disabled==true){

   7:              return false;  

   8:          }

   9:          else{

  10:              //取得使用者確認

  11:              var sure = confirm('Are you sure');

  12:              if(sure==true){

  13:                  //直接disable掉

  14:                  btn.disabled=true;

  15:                  return true;

  16:              }

  17:              else{

  18:                  return false;

  19:              }

  20:          }

  21:      }

  22:  </script>



就這樣。好像沒看到什麼時候解開XD? 因為我原本就有在code裡根據其他數據處理判斷是否enable。所以不必另外處理,每次page_load都會重新設定。搞定。


測試的話,以上面例子來說,動作是在save command裡,可以加個

   1:  System.Threading.Thread.Sleep(5000);


來觀察disable狀態,也可以趁機多按幾次按鈕看是否真的無作用。

Ref:
Friday, June 12, 2009

待研究主題: SQL語法之 IN vs. EXISTS

兩篇討論from Ask Tom:
Thursday, June 11, 2009

SharePoint: Recycle Bin

這兩天稍為研究了一下WSS3.0資源回收桶的運作模式。

以系統預設的狀況來看,可以用下圖來說明:

  1. 使用者從各子網站將任何檔案刪除後,檔案會進入該網站下的資源回收桶。
    此時使用者還可自行從資源回收桶裡回復該檔案。
    資料庫裡與該檔案相關連的資料 [DeleteTransactionId]欄位會被註記為非"0X"的十六進位值。同時在網站集合層級的[使用者資源回收桶項目]下可以看見這個檔案。
  2. 使用者從自己網站下的資源回收桶刪除後,即無法再看見該檔案。
    但並非永久刪除,此時在網站集合層級的[已從使用者資源回收桶項目刪除]的連結下還可看見該檔案,使用者可要求網站管理員幫助回復檔案。
  3. 若檔案在[已從使用者資源回收桶項目刪除]被刪除,就真的從資料庫裡把該筆檔案刪除了。
完畢。
其他細節請看下面參考連結。

Ref:
Wednesday, June 10, 2009

SharePoint: About Deleted Item

重要文件暫記:

c# 3.0 new features Example Demo


   1:  /////////////////////////////////////////////////////

   2:  //

   3:  // 總結所有的 New Features(language extensions)

   4:  //

   5:  /////////////////////////////////////////////////////

   6:   

   7:  using System;

   8:  using System.Collections.Generic;

   9:  using System.Linq;

  10:  using System.Text;

  11:  using System.Diagnostics;

  12:   

  13:  static class newFeaturesDemo

  14:  {

  15:      class ProcessData {

  16:          public Int32 Id { set; get; }

  17:          public Int64 Memory { set; get; }

  18:          public String Name { set; get; }

  19:      }

  20:   

  21:      public static void DisplayProcesses(Func<Process, Boolean> match) {

  22:          

  23:          // 1. implicitly typed local variables

  24:          var processes = new List<ProcessData>();

  25:   

  26:          foreach (var process in Process.GetProcesses()) {

  27:              if (match(process)) {

  28:                  

  29:                  // 2. object initialized

  30:                  processes.Add(new ProcessData

  31:                  {

  32:                      Id = process.Id,

  33:                      Name = process.ProcessName,

  34:                      Memory = process.WorkingSet64

  35:                  });

  36:              }

  37:          }

  38:   

  39:          // 3. extension methods

  40:          Console.WriteLine("Total memeory: {0} MB",

  41:                             processes.TotalMemory()/1024/1024);

  42:   

  43:          // 4. lambda expression

  44:          var top2Memory = processes

  45:                           .OrderByDescending(process => process.Memory)

  46:                           .Take(2)

  47:                           .Sum(process => process.Memory) / 1024 / 1024;

  48:   

  49:          Console.WriteLine(

  50:              "Memory consumed by the two most hungry processes: {0} MB",

  51:              top2Memory);

  52:   

  53:          // 5. anonymous type

  54:          var results = new

  55:          {

  56:              TotalMemory = processes.TotalMemory() / 1024 / 1024,

  57:              Top2Memory = top2Memory,

  58:              Processes = processes

  59:          };

  60:          

  61:          ObjectDumper.Write(results, 1);

  62:          ObjectDumper.Write(processes);

  63:   

  64:      }

  65:   

  66:      static Int64 TotalMemory(this IEnumerable<ProcessData> processes) {

  67:          Int64 result = 0;

  68:          foreach (var process in processes) {

  69:              result += process.Memory;

  70:          }

  71:   

  72:          return result;

  73:      }

  74:   

  75:    static void Main()

  76:    {

  77:      DisplayProcesses(

  78:        process => process.WorkingSet64 >= 20*1024*1024);

  79:    }     

  80:  }


Thursday, June 04, 2009

c# 3.0 new features (part II)

前一篇已經很長了,不想再拉長他的篇幅,所以分篇寫。而且這個趴吐也是相當模糊的不熟悉XD

New Feature #3: Lambda(λ) expressions
講這個之前呢,必須先知道有個delegates(委派)這東西。至於什麼是委派呢... 我也不是很清楚
= =,相當慚愧(orz) 所以才在上一篇貼了個文件XD。大概看得懂啦,不過不知道該怎麼寫。而且也還沒搞懂為什麼要這麼做(他存在的目的?)。

原本的delegates因為有了anonymous methods(匿名方法)而更簡潔。
現在要介紹的lambada expressions就是再進一步精簡他。

下面這個範例來自MSDN,裡面就包含了以具名、匿名,或這裡的重點,以lambda expression來 instantiate(實體化?) delegates:

   1:  // Declare delegate -- defines required signature:

   2:  delegate double MathAction(double num);

   3:   

   4:  class DelegateTest

   5:  {

   6:      // Regular method that matches signature:

   7:      static double Method4Delegates(double input)

   8:      {

   9:          return input * 2;

  10:      }

  11:   

  12:      static void Main()

  13:      {

  14:          // Instantiate delegate with named method(具名方法):

  15:          MathAction ma = Method4Delegates;

  16:   

  17:          // Invoke delegate ma:

  18:          double multByTwo = ma(4.5);

  19:          Console.WriteLine(multByTwo);

  20:   

  21:          // Instantiate delegate with anonymous method(匿名方法):

  22:          MathAction ma2 = delegate(double input)

  23:          {

  24:              return input * input;

  25:          };

  26:   

  27:          double square = ma2(5);

  28:          Console.WriteLine(square);

  29:   

  30:          // Instantiate delegate with lambda expression

  31:          MathAction ma3 = s => s * s * s;

  32:          double cube = ma3(4.375);

  33:   

  34:          Console.WriteLine(cube);

  35:      }

  36:  }

  37:   


New Feature #4: Extension methods
這個新功能也是個好東西,也一樣很難描述,所以一樣貼貼重點。

This new language feature makes it possible to treat existing types as if they were extended with additional methods.

In order to transform our method into an extension method, all we have to do is add the this keyword to the first parameter. The this keyword instructs the compiler to treat the method as an extension method.

小小看一下他的作用:

這裡有一小行code, 大概先把一堆processes做了些篩選,然後計算篩選出來的processes所佔用的memory, 最後做一個單位的換算。

BytesToMegaBytes(TotalMemory(FilterOutSomeProcesses(processes)));

嗯,對阿,然後呢? 然後如果把剛剛那些method變成extension method的話,就可以長成這樣:

processes
.FilterOutSomeProcesses()
.TotalMemory()
.BytesToMegaBytes();

上面那段code是為了方便閱讀才分成4行的,不是什麼特殊寫法XD。而且,看起來好像FilterOutSomeProcesses(), TotalMemory(), BytesToMegaBytes()就是processes的static method一樣,用個"."(dot)就可以叫用這些功能,他們其實是extension methods~ 酷吧~

但是!!! 以上面的code來說,如果processes其實也有一個instance method叫做TotalMemory呢? 在C#裡(VB.NET不太一樣), 如果extension method跟instance method都符合叫用條件的話,會優先呼叫該instance本身的method。

下面這個example就可以看出來:

   1:  using System;

   2:   

   3:  class Class1 {}

   4:  class Class2 {

   5:    public void Method1(string s) { Console.WriteLine("Class2.Method1");}

   6:  }

   7:  class Class3 {

   8:    public void Method1(object o) { Console.WriteLine("Class3.Method1");}

   9:  }

  10:  class Class4 {

  11:    public void Method1(int i) { Console.WriteLine("Class4.Method1");}

  12:  }

  13:  static class Extensions {

  14:    static public void Method1(this object o, int i)

  15:    {

  16:      Console.WriteLine("Extensions.Method1");

  17:    }

  18:   

  19:    static void Main()

  20:    {

  21:      new Class1().Method1(12);

  22:      new Class2().Method1(12);

  23:      new Class3().Method1(12);

  24:      new Class4().Method1(12);

  25:    }

  26:  }

  27:   

  28:  // Answer:

  29:  // Extensions.Method1

  30:  // Extensions.Method1

  31:  // Class3.Method1

  32:  // Class4.Method1


New Features #1, #2 請看c# 3.0 new features

Delegates

阿... 還不懂,收個文件。
Both delegates and interfaces enable a class designer to separate type declarations and implementation. A given interface can be inherited and implemented by any class or struct. A delegate can be created for a method on any class, as long as the method fits the method signature for the delegate.

A delegate can be instantiated by associating it either with a named or anonymous method.
Wednesday, June 03, 2009

c# 3.0 new features

前幾個禮拜一直想好好寫一下auto-implemented properties這個主題,拖了一陣子,忽然覺得他沒什麼= =,就不想寫了。發現了個更讓人感興趣的東西,所以就一起寫在這。

New Feature #1: auto-implemented properties
懶的描述,請看連結XD

New Feature #2: Object and collection initializers
這一塊是我感興趣的部分。直接看程式:

   1:  ProcessData data = new ProcessData();

   2:  data.Id = 123;

   3:  data.Name = "MyProcess";

   4:  data.Memory = 123456;

上面這段程式是很常見的片段: 宣告ProcessDate的object後,初始化一些值。
用C#3.0可以寫成這樣:

var data = new ProcessData{ Id=123, Name="MyProcess", Memory=123456};

嗯, 是認真的。

如果是有constructor的class:

   1:  var exception = new Exception("message");

   2:  exception.Source = "LINQ in Action";

   3:  throw exception;


可以變成這樣:

throw new Exception("message") { Source = "LINQ in Action" };

相當over!!! 以上介紹的是所謂的"Object Initializer", 接下來看看"collection initializer", 他其實並不陌生:

var digits = new List<int> {0, 1, 2, 3, 4, 5, 6, 7, 8, 9};

這看起來超眼熟的,他原本應該是這樣:

   1:  List<int> digits = new List<int>();

   2:  digits.Add(0);

   3:  digits.Add(1);

   4:  digits.Add(2);

   5:  //....

   6:  digits.Add(9);


再來一個稍微麻煩一點的:

   1:  ProcessData tmp;

   2:  var processes = new List<ProcessData>();

   3:  //先來第一組資料

   4:  tmp = new ProcessData();

   5:  tmp.Id = 123;

   6:  tmp.Name = "devenv";

   7:  processes.Add(tmp);

   8:  //再來第二組資料

   9:  tmp = new ProcessData();

  10:  tmp.Id = 456;

  11:  tmp.Name = "firefox";

  12:  processes.Add(tmp);


把ojbect initializer跟collection initializer一起用:

   1:  var processes = new List<ProcessData> {

   2:    new ProcessData {Id=123, Name="devenv"},

   3:    new ProcessData {Id=456, Name="firefox"}

   4:  }


相當簡潔明瞭。以上,要這樣做,必須有一個前提XD(這麼晚才講)

This new syntax allows us to initialize different types of collections, provided they implement System.Collections.IEnumerable and provide suitable Add methods.

(take a break~) 好像還有,讀完後補。

PowerBuilder problems

今天整個早上都在跟pb奮戰。遇到幾個詭異的問題=   =

1. function忽然壞掉
自己寫的某個function不知道發生了什麼事情,忽然就罷工了。就是程式跑到那,就直接跳過 他。就像有一支funcion會回傳boolean,然後放在if區段裡,程式跑到那,根本不會進去那支 function就跳到else去了... 相當傻眼。搞了半天,可以嘗試做一下Regenerate,搞定。

2. 資料庫欄位長度問題
這個狀況有點複雜,就是兩間公司有自己的資料庫,可是跑的是同樣的系統,同樣的程式。但是資料庫的結構又有那麼點不同,這次遇到的是欄位長度不同。所以某個data window的該欄位在P公司(欄位長度較短)跑起來是正常的,可是在O公司資料卻被截斷了。明明就連到O公司的資料庫了,程式還是顯示P公司資料庫的長度。原本以為長度被寫死了,後來知道原來可以在那個data window按右鍵,選"Edit Source"。可以發現原來column的型別與長度被定義在這裡面,就從這兒給他改掉,顯示上是沒問題,不過目前還不確定如果要操作這筆資料會不會有問題。

這樣,搞一個早上,還有其他零零碎碎的。

Tuesday, May 26, 2009

ORA-01720: grant option does not exist for 'XXX'

今天因為程式需求,需要做一件看起來很詭異的事情。大概是這樣:
情境1:
資料庫裡有A跟F兩個使用者。A使用者下有一個table: B。我要在F使用者下新建一個view: B,內容跟A(user)的B(table)完全一樣。
到目前為止其實還好。就是先grant select B(table)的權限給F(user)即可成功的建起view B。

情境2: (問題在這)
這個F(user)下的B(view)是什麼用途呢~? 是要給A(user)用的XD。所以我說這是件詭異的事情,自己有資料不用,偏偏要去用別人的XD(特殊需求特殊需求~)。
照說如果A(user)要可以select F(user)下的B(view),那也應該做跟上面一樣的事情: grant select B(view)的權限給A(user)。
就在這個moment!! 如果這麼做,就會收到如標題那樣的錯誤訊息。

至於為什麼呢? 這樣說好了,我今天答應A給他"參考"我的作業,如果A沒經過我的同意,又把我的作業給C看,那算什麼!!! 分數三等份阿!!! 怎麼行呢? XD

假如我答應借A看我的作業的同時,也說: "去散播我的愛吧~"(就是你可以自行把我的東西在借給下個人),那樣就不會有問題。所以回到資料庫上也一樣。在授權給F(user)的時候,必須准許他也可以授權給別人:
SQL> grant select on A.B to F with grant option;

that's all!! 這樣F(user)的B(view)也就能再做授權給別人的動作了(即使那個人是A)。

寫完還要檢查一下那些A阿F阿B阿table阿view阿有沒有搞錯=   = 小複雜

Thursday, May 21, 2009

Linq #1: Getting Started

這兩天花了一點時間大概看了一些What is Linq? Linq's design goal. Why Linq? History等不是很想看的東西。
With LINQ, Microsoft's intention was to provide a solution for the problem of object-relational mapping, as well as to simplify the interaction between objects and data sources.

這是我唯幾有畫的段落=    =,不知道究竟是不是個key。還是比較想來體驗一下code。
跟hello world一樣,首先要來個hello linq:


   1:  using System;

   2:  using System.Linq;

   3:   

   4:  static class HelloWorld

   5:  {

   6:    static void Main()

   7:    {

   8:      //先來個collection

   9:      string[] words = 

  10:         { "hello", "wonderful", "linq", "beautiful", "world" };

  11:      

  12:      //傳說中的linq語法在這from~ where~ select

  13:      var shortWords =   

  14:        from word in words

  15:        where word.Length <= 5

  16:        select word;

  17:   

  18:      //把剛剛處理好的資料印出來,結果就是: hello linq world 各一行

  19:      foreach (var word in shortWords)

  20:        Console.WriteLine(word);

  21:    }

  22:  }


Linq特別強調data query不再只是一串string,他變成是程式的一部份,所以你不會在執行程式時才發現sql下錯了、字拼錯、參數名字打錯這類的錯誤。Linq背後可存取的資料來源很多種,不管是存取資料庫或只是一個collection,只要學了Linq,就可以用統一的方法對這些資料來源進行存取。

再來一段長一點的,下面要表達的是,Linq也可以把資料弄成XML的樣子,重點是: 輕易地


   1:  using System;

   2:  using System.Linq;

   3:  using System.Xml;

   4:  using System.Xml.Linq;

   5:   

   6:  class Book

   7:  {

   8:    public string Publisher;

   9:    public string Title;

  10:    public int    Year;

  11:    public Book(string title, string publisher, int year)

  12:    {

  13:      Title = title;

  14:      Publisher = publisher;

  15:      Year = year;

  16:    }

  17:  }

  18:   

  19:  static class HelloLinqToXml

  20:  {

  21:    static void Main()

  22:    {

  23:        //用上面那個book class產生3筆資料

  24:        Book[] books = new Book[] {             

  25:        new Book("Ajax in Action", "Manning", 2005),

  26:        new Book("Windows Forms in Action", "Manning", 2006),

  27:        new Book("RSS and Atom in Action", "Manning", 2006)

  28:        };

  29:   

  30:      //重頭戲: 只能意會不能言傳XD

  31:      XElement xml = new XElement("books",  // layer1

  32:        from book in books

  33:        where book.Year == 2006

  34:        select new XElement("book",  //layer2

  35:          new XAttribute("title", book.Title),  // attribute of book(layer2)

  36:          new XElement("publisher", book.Publisher)  //layer3

  37:        )

  38:      );

  39:      Console.WriteLine(xml);

  40:   

  41:      //result:

  42:   

  43:          //<books>                                     ==> layer1

  44:          //  <book title="Windows Forms in Action">    ==> layer2 with attribute(title)

  45:          //    <publisher>Manning</publisher>          ==> layer3

  46:          //  </book>

  47:          //  <book title="RSS and Atom in Action">

  48:          //    <publisher>Manning</publisher>

  49:          //  </book>

  50:          //</books>

  51:    }

  52:  }


接下來應該是最常應用的: 連接資料庫


   1:  using System;

   2:  using System.Linq;

   3:  using System.Data.Linq;

   4:  using System.Data.Linq.Mapping;

   5:   

   6:  static class HelloLinqToSql

   7:  {

   8:     //declaring the classes to represent the application data: entities

   9:     //mapping object and database by adding customer attritube

  10:    [Table(Name="Contacts")]

  11:    class Contact

  12:    {

  13:      [Column(IsPrimaryKey=true)]

  14:      public int ContactID { get; set; }

  15:      [Column(Name="ContactName")]

  16:      public string Name { get; set; }

  17:      [Column]

  18:      public string City { get; set; }

  19:    }

  20:   

  21:    static void Main()

  22:    {

  23:      string path =   //使用northwind資料庫

  24:        System.IO.Path.GetFullPath(@"..\..\Data\northwnd.mdf");

  25:      //translate requests for objects into SQL queries

  26:      DataContext db = new DataContext(path);

  27:   

  28:      var contacts =                     

  29:        from contact in db.GetTable<Contact>()

  30:        where contact.City == "Paris"

  31:        select contact;

  32:   

  33:      foreach (var contact in contacts)        

  34:        Console.WriteLine("Bonjour "+contact.Name);

  35:    }

  36:  }


完畢。上面那一段程式,Linq做掉了一些東西:
  1. 連接資料庫
  2. 自動轉換SQL query
  3. 執行SQL

....如此一般如此一般.... 他其實還是有點複雜的...

Tags

Archivo